WinHTTP 会话概览

WinHTTP 会话概览WinHTTP会话概览TheMicrosoftWindowsHTTPServices(WinHTTP)exposesasetofC/C++functionsthatenableyourapplicationtoaccessHTTPresourcesontheWeb.Thistopicprovidesanoverviewofho

大家好,又见面了,我是你们的朋友全栈君。

WinHTTP 会话概览

The Microsoft Windows HTTP Services (WinHTTP) exposes a set of C/C++ functions that enable your application to access HTTP resources on the Web. This topic provides an overview of how these functions are used to interact with an HTTP server.

微软的HTTP服务(WinHTTP)暴露了一些C++函数,这些函数能让你的程序访问Web网络上的HTTP资源。这篇文章告诉你怎么使用这些函数和HTTP服务器进行交互。

使用 WinHTTP API 访问 Web

The following diagram shows the order in which WinHTTP functions are typically called when interacting with an HTTP server. The shaded boxes represent functions that generate anHINTERNET handle, while the plain boxes represent functions that use those handles.

下面的流程图显示了和HTTP服务器使用WinHTTP函数的典型应用。带阴影的框表示这些函数会产生HINTERNET句柄,白框中的函数会用到这些句柄。

Functions that create handles

初始化 WinHTTP

Before interacting with a server, WinHTTP must be initialized by calling WinHttpOpen. WinHttpOpen creates a session context to maintain details about the HTTP session, and returns a session handle.Using this handle, theWinHttpConnect function is then able to specify a target HTTP or Secure Hypertext Transfer Protocol (HTTPS) server.

开始和服务器交互前,WinHTTP必须使用WinHttpOpen进行初始化,WinHttpOpen会创建一个会话Context,这个会话Context包含了HTTP会话的细节,并且把这个会话Context的句柄返回。使用这个句柄,WinHttpConnect函数就可以指定一个目标HTTP或HTTPS服务器。

Note  A call to
WinHttpConnect does not result in an actual connection to the HTTP server until a request is made for a specific resource.

注意 对
WinHttpConnect的调用不会立即产生与HTTP服务器的连接请求,连接请求实在请求具体的资源时产生的。

打开一个请求

The WinHttpOpenRequest function opens an HTTP request for a particular resource and returns anHINTERNET handle that can be used by the other HTTP functions. WinHttpOpenRequest does not send the request to the server when called. TheWinHttpSendRequest function actually establishes a connection over the network and sends the request.

WinHttpOpenRequest函数为特定的资源打开一个HTTP请求,然后返回一个HINTERNET句柄,这个句柄可以被其他HTTP函数使用。WinHttpOpenRequest也不会向服务器发送数据。WinHttpSendRequest函数才会与服务器建立连接并发送请求。

The following example shows a sample call to WinHttpOpenRequest that uses the default options.

下面是使用默认参数调用WinHttpOpenRequest的例子。

HINTERNET hRequest = WinHttpOpenRequest( hConnect, L"GET", NULL, NULL, NULL, NULL, 0);

添加请求头部

The WinHttpAddRequestHeaders function allows an application to append additional free-format request headers to the HTTP request handle. It is intended for use by sophisticated applications that require precise control over the requests sent to the HTTP server.

WinHttpAddRequestHeaders函数允许应用程序向HTTP请求中添加各种格式的头部信息。这样让客户端与服务器实现复杂应用与精细控制。

The WinHttpAddRequestHeaders function requires an HTTP request handle created byWinHttpOpenRequest, a string that contains the headers, the length of the headers, and any modifiers.

WinHttpAddRequestHeaders函数需要一个WinHttpOpenRequest产生的HTTP请求句柄,

The following modifiers can be used with WinHttpAddRequestHeaders.

WinHttpAddRequestHeaders可以实现下面改变

Modifier Description
WINHTTP_ADDREQ_FLAG_ADD

Adds the header if it does not exist. Used with WINHTTP_ADDREQ_FLAG_REPLACE.

如果头部不存在,添加它

WINHTTP_ADDREQ_FLAG_ADD_IF_NEW

Adds the header only if it does not already exist; otherwise, an error is returned.

如果头部确实不存在才添加,否则返回错误。

WINHTTP_ADDREQ_FLAG_COALESCE

Merges headers of the same name.

对同名头部信息进行融合

WINHTTP_ADDREQ_FLAG_COALESCE_WITH_COMMA

Merges headers of the same name using a comma. For example, adding “Accept: text/*” followed by “Accept: audio/*” with this flag forms the single header “Accept: text/*, audio/*”, causing the first header found to be merged. It is up to the calling application to ensure a cohesive scheme with respect to merged/separate headers.

WINHTTP_ADDREQ_FLAG_COALESCE_WITH_SEMICOLON Merges headers of the same name using a semicolon.
WINHTTP_ADDREQ_FLAG_REPLACE Replaces or removes a header. If the header value is empty and the header is found, it is removed. If the header value is not empty, the header value is replaced.

 

发送请求

The WinHttpSendRequest function establishes a connection to the server and sends the request to the specified site. This function requires anHINTERNET handle created by WinHttpOpenRequest. WinHttpSendRequest can also send additional headers or optional information. The optional information is generally used for operations that write information to the server, such as PUT and POST.

WinHttpSendRequest函数与服务器建立一个连接,这个函数需要使用WinHttpOpenRequest产生的句柄。WinHttpSendRequest也可以发送附加头部或可选信息,这些附加信息一般是用来向服务器写信息的,例如PUT或者POST。

After the WinHttpSendRequest function sends the request, the application can use theWinHttpReadData and WinHttpQueryDataAvailable functions on the HINTERNET handle to download the server’s resources.

WinHttpSendRequest函数发送数据后,应用程序可以使用WinHttpReadDataWinHttpQueryDataAvailable函数,在HINTERNET句柄上下载服务器资源。

向服务器发送数据

To post data to a server, the HTTP verb in the call to WinHttpOpenRequest must be either POST or PUT. When WinHttpSendRequest is called, the dwTotalLength parameter should be set to the size of the data in bytes. Then useWinHttpWriteData to post the data to the server.

要想服务器发送数据,WinHttpOpenRequest的HTTP verb参数必须是POST或PUT。当调用WinHttpSendRequest时,dwTotalLength参数应该设置为要发送数据的byte大小。然后使用WinHttpWriteData向服务器发送数据。

Alternatively, set the lpOptional parameter of WinHttpSendRequest to the address of a buffer that contains data to post to the server. When using this technique, you must set both thedwOptionalLength anddwTotalLength parameters of WinHttpSendRequest to be the size of the data being posted. CallingWinHttpSendRequest in this manner eliminates the need to callWinHttpWriteData.

另外,设置WinHttpSendRequestlpOptional参数为一个缓冲,这个缓冲中包含要发送的数据。当使用这项技术时,你必须设置WinHttpSendRequest中的dwOptionalLength 和dwTotalLength参数,这些参数由要发送的数据决定。调用WinHttpSendRequest后需要调用WinHttpWriteData

获取请求后的信息

The WinHttpQueryHeaders function allows an application to retrieve information about an HTTP request. The function requires anHINTERNET handle created by WinHttpOpenRequest, an information level value, and a buffer length.WinHttpQueryHeaders also accepts a buffer that stores the information and a zero-based header index that enumerates multiple headers with the same name.

WinHttpQueryHeaders函数允许应用获取HTTP请求中的信息,这个函数需要WinHttpOpenRequest产生的请求句柄,信息级别值和缓冲长度。WinHttpQueryHeaders也接受一个缓冲,这个缓冲中存储着一些信息,和同名的以0序号开始的头部信息。

Use any of the information level values found on the Query Info Flags page with a modifier to control the format in which the information is stored in thelpvBuffer parameter ofWinHttpQueryHeaders.

使用任意可在Query Info Flags页找到的水平值来控制存在WinHttpQueryHeaders函数的lpvBuffer参数里的格式。

从Web上下载资源

After opening a request with the WinHttpOpenRequest function, sending it to the server with WinHttpSendRequest, and preparing the request handle to receive a response withWinHttpReceiveResponse, the application can use the WinHttpReadData and WinHttpQueryDataAvailable functions to download the resource from the HTTP server.

在使用WinHttpOpenRequest打开资源后,使用WinHttpSendRequest向服务器发送请求,准备好WinHttpReceiveResponse的句柄来获取服务器响应。可以使用WinHttpReadData and WinHttpQueryDataAvailable从服务器下载资源。

The following sample code shows how to download a resource with secure transaction semantics. The sample code initializes the WinHTTP application programming interface (API), selects a target HTTPS server, and then opens and sends a request for this secure resource. WinHttpQueryDataAvailable is used with the request handle to determine how much data is available for download, and thenWinHttpReadData is used to read that data. This process is repeated until the entire document has been retrieved and displayed.

下面例程中展示了一个如何使用安全语法下载资源,这个例程初始化WinHTTP程序,选择目标HTTPS服务器,然后打开,发送请求。WinHttpQueryDataAvailable被用来探查有多少数据需要下载,然后使用WinHttpReadData获取这些数据,这个过程一直重复,直到整个文档被下载并且展示。

C++

#include <windows.h>
#include <winhttp.h>
#include <stdio.h>

#pragma comment(lib,"Winhttp.lib")


int main()
{
    
    DWORD dwSize = 0;
    DWORD dwDownloaded = 0;
    LPSTR pszOutBuffer;
    BOOL  bResults = FALSE;
    HINTERNET  hSession = NULL, 
        hConnect = NULL,
        hRequest = NULL;
    
    // Use WinHttpOpen to obtain a session handle.
    hSession = WinHttpOpen( L"WinHTTP Example/1.0",  
                       WINHTTP_ACCESS_TYPE_DEFAULT_PROXY,
                       WINHTTP_NO_PROXY_NAME, 
                       WINHTTP_NO_PROXY_BYPASS, 0 );
    
    // Specify an HTTP server.
    if( hSession )
        hConnect = WinHttpConnect( hSession, L"192.168.1.101",
                          INTERNET_DEFAULT_HTTPS_PORT, 0 );
    
    // Create an HTTP request handle.
    if( hConnect )
        hRequest = WinHttpOpenRequest( hConnect, L"GET", NULL,
        NULL, WINHTTP_NO_REFERER, 
        WINHTTP_DEFAULT_ACCEPT_TYPES, 
        WINHTTP_FLAG_SECURE );
    
    // Send a request.
    if( hRequest )
        bResults = WinHttpSendRequest( hRequest,
        WINHTTP_NO_ADDITIONAL_HEADERS, 0,
        WINHTTP_NO_REQUEST_DATA, 0, 
        0, 0 );
    
    
    // End the request.
    if( bResults )
        bResults = WinHttpReceiveResponse( hRequest, NULL );
    
    // Keep checking for data until there is nothing left.
    if( bResults )
    {
        do 
        {
            // Check for available data.
            dwSize = 0;
            if( !WinHttpQueryDataAvailable( hRequest, &dwSize ) )
                printf( "Error %u in WinHttpQueryDataAvailable.\n",
                GetLastError( ) );
            
            // Allocate space for the buffer.
            pszOutBuffer = new char[dwSize+1];
            if( !pszOutBuffer )
            {
                printf( "Out of memory\n" );
                dwSize=0;
            }
            else
            {
                // Read the data.
                ZeroMemory( pszOutBuffer, dwSize+1 );
                
                if( !WinHttpReadData( hRequest, (LPVOID)pszOutBuffer, 
                    dwSize, &dwDownloaded ) )
                    printf( "Error %u in WinHttpReadData.\n", GetLastError( ) );
                else
                    printf( "%s", pszOutBuffer );
                
                // Free the memory allocated to the buffer.
                delete [] pszOutBuffer;
            }
        } while( dwSize > 0 );
    }
    
    
    // Report any errors.
    if( !bResults )
        printf( "Error %d has occurred.\n", GetLastError( ) );
    
    // Close any open handles.
    if( hRequest ) WinHttpCloseHandle( hRequest );
    if( hConnect ) WinHttpCloseHandle( hConnect );
    if( hSession ) WinHttpCloseHandle( hSession );
    
    return 0; 
}



PS:自己编译时,发现程序会返回12175错误,下面是12175的错误解决方法,加在    
if( hConnect )
        hRequest = WinHttpOpenRequest( hConnect, L"GET", NULL,
        NULL, WINHTTP_NO_REFERER, 
        WINHTTP_DEFAULT_ACCEPT_TYPES, 
        WINHTTP_FLAG_SECURE );
之后就可以了。

------------------------------------------------------------------

     
     
     
     DWORD  dwFlags;
     DWORD  dwBuffLen =  sizeof (dwFlags);           
     WinHttpQueryOption (hRequest, WINHTTP_OPTION_SECURITY_FLAGS,
         ( LPVOID )&dwFlags, &dwBuffLen);
     dwFlags |= SECURITY_FLAG_IGNORE_UNKNOWN_CA;
     dwFlags |= SECURITY_FLAG_IGNORE_CERT_DATE_INVALID;
     dwFlags |= SECURITY_FLAG_IGNORE_CERT_CN_INVALID;
//    dwFlags |= SECURITY_FLAG_IGNORE_CERT_WRONG_USAGE;
 
     WinHttpSetOption (hRequest, WINHTTP_OPTION_SECURITY_FLAGS,
         &dwFlags,  sizeof  (dwFlags) );
 

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/157534.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)


相关推荐

  • laravel的ORM模型的find(),findOrFail(),first(),firstOrFail(),get(),list(),toArray()之间的区别…

    laravel的ORM模型的find(),findOrFail(),first(),firstOrFail(),get(),list(),toArray()之间的区别…

  • 全局服务器负载均衡(GSLB)简介

    全局服务器负载均衡(GSLB)简介引言在过去的几年中,随着互联网的快速发展和企业应用WEB化,服务器负载均衡(SLB)技术已经不再陌生。服务器负载均衡根据用户数据请求中的4-7层信息将其智能转发到后端少则数台多则成百上千台应用服务器,并且确保根据事先定义的策略选择最佳的服务器进行转发,从而一定程度上解决了应用的可用性、扩展性等问题。但是,随着用户对应用可用性和扩展性需求的进一步增加,越来越多的用户不满足于在单一数据

  • ProgressDialog总结

    ProgressDialog总结ProgressDialog的使用 ProgressDialog继承自AlertDialog,AlertDialog继承自Dialog,实现DialogInterface接口。 ProgressDialog的创建方式有两种,一种是newDialog,一种是调用Dialog的静态方法Dialog.show()。 //方式一:newDialog finalProgr…

  • ps入门视频全套教程零基础,ps教程百度云分享新手必看!「建议收藏」

    ps入门视频全套教程零基础,ps教程百度云分享新手必看!「建议收藏」链接:https://pan.baidu.com/s/1pQmEc-XgquF1jBXIoS6-Gg提取码:lcrw自学PS的第一步:安装软件!遇到过很多想学PS的伙伴,60%的新手都折在了软件安装这一步。新版PS一定比旧版好用,别听那些“大神”的言论,他们只是对曾经需要大力气去人工实现的功能被新版一键取代的感觉不爽罢了。第二步:想清楚学习PS的目的安装好PS,你就要想想学习PS的目的是啥了。如果你只是平时做个套版海报,帮女朋友P个照片,抠个图,免费的教程足够!但是..

  • 详解shell语法检查模式

    详解shell语法检查模式启用verbose调试模式在进入本指导的重点之前,让我们简要地探索下verbose模式。它可以用-v调试选项来启用,它会告诉shell在读取时显示每行。要展示这个如何工作,下面是一个示例脚本来批量将PNG图片转换成JPG格式。将下面内容输入(或者复制粘贴)到一个文件中。#!/bin/bash#convertforimagein*.png;docon

  • python利用cookie登录(python爬虫教程pdf)

    http://blog.csdn.net/pipisorry/article/details/47948065实战1:使用cookie登录哈工大ACM网站获取网站登录地址http://acm.hit.edu.cn/hoj/system/login查看要传送的post数据user和passwordCode:#!/usr/bin/envpython#-*-

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号