Função WinHttpSendRequest (winhttp.h)

A função WinHttpSendRequest envia a solicitação especificada para o servidor HTTP.

Sintaxe

WINHTTPAPI BOOL WinHttpSendRequest(
  [in]           HINTERNET hRequest,
  [in, optional] LPCWSTR   lpszHeaders,
  [in]           DWORD     dwHeadersLength,
  [in, optional] LPVOID    lpOptional,
  [in]           DWORD     dwOptionalLength,
  [in]           DWORD     dwTotalLength,
  [in]           DWORD_PTR dwContext
);

Parâmetros

[in] hRequest

Um identificador HINTERNET retornado por WinHttpOpenRequest.

[in, optional] lpszHeaders

Um ponteiro para uma cadeia de caracteres que contém os cabeçalhos adicionais a serem acrescentados à solicitação. Esse parâmetro poderá ser WINHTTP_NO_ADDITIONAL_HEADERS se não houver cabeçalhos adicionais para acrescentar.

[in] dwHeadersLength

Um valor inteiro longo sem sinal que contém o comprimento, em caracteres, dos cabeçalhos adicionais. Se esse parâmetro for -1L e pwszHeaders não for NULL, essa função pressupõe que pwszHeaders seja encerrado em nulo e o comprimento será calculado.

[in, optional] lpOptional

Um ponteiro para um buffer que contém todos os dados opcionais a serem enviados imediatamente após os cabeçalhos de solicitação. Esse parâmetro geralmente é usado para operações POST e PUT. Os dados opcionais podem ser o recurso ou os dados postados no servidor. Esse parâmetro poderá ser WINHTTP_NO_REQUEST_DATA se não houver dados opcionais a serem enviados.

Se o parâmetro dwOptionalLength for 0, esse parâmetro será ignorado e definido como NULL.

Esse buffer deve permanecer disponível até que o identificador de solicitação seja fechado ou a chamada para WinHttpReceiveResponse seja concluída.

[in] dwOptionalLength

Um valor inteiro longo sem sinal que contém o comprimento, em bytes, dos dados opcionais. Esse parâmetro poderá ser zero se não houver dados opcionais a serem enviados.

Esse parâmetro deve conter um comprimento válido quando o parâmetro lpOptional não for NULL. Caso contrário, lpOptional será ignorado e definido como NULL.

[in] dwTotalLength

Um valor inteiro longo sem sinal que contém o comprimento, em bytes, do total de dados enviados. Esse parâmetro especifica o cabeçalho Content-Length da solicitação. Se o valor desse parâmetro for maior que o comprimento especificado por dwOptionalLength, WinHttpWriteData poderá ser usado para enviar dados adicionais.

dwTotalLength não deve alterar entre chamadas para WinHttpSendRequest para a mesma solicitação. Se dwTotalLength precisar ser alterado, o chamador deverá criar uma nova solicitação.

[in] dwContext

Um ponteiro para uma variável do tamanho de um ponteiro que contém um valor definido pelo aplicativo que é passado, com o identificador de solicitação, para quaisquer funções de retorno de chamada.

Retornar valor

Retorna TRUE se tiver êxito ou FALSE caso contrário. Para obter informações de erro estendidas, chame GetLastError. Os códigos de erro são listados na tabela a seguir.

Código do Erro Descrição
ERROR_WINHTTP_CANNOT_CONNECT
Retornado se a conexão com o servidor falhou.
ERROR_WINHTTP_CLIENT_AUTH_CERT_NEEDED
O servidor HTTP seguro requer um certificado do cliente. O aplicativo recupera a lista de emissores de certificado chamando WinHttpQueryOption com a opção WINHTTP_OPTION_CLIENT_CERT_ISSUER_LIST .

Se o servidor solicitar o certificado do cliente, mas não o exigir, o aplicativo poderá alternar chamar WinHttpSetOption com a opção WINHTTP_OPTION_CLIENT_CERT_CONTEXT . Nesse caso, o aplicativo especifica a macro WINHTTP_NO_CLIENT_CERT_CONTEXT no parâmetro lpBuffer de WinHttpSetOption. Para obter mais informações, consulte a opção WINHTTP_OPTION_CLIENT_CERT_CONTEXT . Windows Server 2003 com SP1, Windows XP com SP2 e Windows 2000: Não há suporte para esse erro.

ERROR_WINHTTP_CONNECTION_ERROR
A conexão com o servidor foi redefinida ou encerrada ou um protocolo SSL incompatível foi encontrado. Por exemplo, o WinHTTP versão 5.1 não dá suporte ao SSL2, a menos que o cliente o habilite especificamente.
ERROR_WINHTTP_INCORRECT_HANDLE_STATE
A operação solicitada não pode ser executada porque o identificador fornecido não está no estado correto.
ERROR_WINHTTP_INCORRECT_HANDLE_TYPE
O tipo de identificador fornecido está incorreto para esta operação.
ERROR_WINHTTP_INTERNAL_ERROR
Ocorreu um erro interno.
ERROR_WINHTTP_INVALID_URL
A URL é inválida.
ERROR_WINHTTP_LOGIN_FAILURE
Falha na tentativa de logon. Quando esse erro é encontrado, o identificador de solicitação deve ser fechado com WinHttpCloseHandle. Um novo identificador de solicitação deve ser criado antes de tentar novamente a função que originalmente produziu esse erro.
ERROR_WINHTTP_NAME_NOT_RESOLVED
O nome do servidor não pode ser resolvido.
ERROR_WINHTTP_OPERATION_CANCELLED
A operação foi cancelada, geralmente porque o identificador no qual a solicitação estava operando foi fechado antes da conclusão da operação.
ERROR_WINHTTP_RESPONSE_DRAIN_OVERFLOW
Retornado quando uma resposta de entrada excede um limite interno de tamanho WinHTTP.
ERROR_WINHTTP_SECURE_FAILURE
Um ou mais erros foram encontrados no certificado SSL (protocolo SSL) enviado pelo servidor. Para determinar que tipo de erro foi encontrado, verifique por meio de uma notificação de WINHTTP_CALLBACK_STATUS_SECURE_FAILURE em uma função de retorno de chamada status. Para obter mais informações, consulte WINHTTP_STATUS_CALLBACK.
ERROR_WINHTTP_SHUTDOWN
O suporte à função WinHTTP é desligado ou descarregado.
ERROR_WINHTTP_TIMEOUT
Tempo limite da solicitação excedido.
ERROR_WINHTTP_UNRECOGNIZED_SCHEME
A URL especificou um esquema diferente de "http:" ou "https:".
ERROR_NOT_ENOUGH_MEMORY
Não havia memória suficiente disponível para concluir a operação solicitada. (Código de erro do Windows)

Windows Server 2003, Windows XP e Windows 2000: O intervalo de reserva TCP definido com a opção WINHTTP_OPTION_PORT_RESERVATION não é grande o suficiente para enviar essa solicitação.

ERROR_INVALID_PARAMETER
O comprimento do conteúdo especificado no parâmetro dwTotalLength não corresponde ao comprimento especificado no cabeçalho Content-Length.

O parâmetro lpOptional deve ser NULL e o parâmetro dwOptionalLength deve ser zero quando o cabeçalho Transfer-Encoding estiver presente.

O cabeçalho Comprimento do Conteúdo não pode estar presente quando o cabeçalho Transfer-Encoding estiver presente.

ERROR_WINHTTP_RESEND_REQUEST
O aplicativo deve chamar WinHttpSendRequest novamente devido a um desafio de redirecionamento ou autenticação.

Windows Server 2003 com SP1, Windows XP com SP2 e Windows 2000: Não há suporte para esse erro.

Comentários

Mesmo quando WinHTTP é usado no modo assíncrono, ou seja, quando WINHTTP_FLAG_ASYNC foi definido no WinHttpOpen, essa função pode operar de forma síncrona ou assíncrona. Em ambos os casos, se a solicitação for enviada com êxito, o aplicativo será chamado novamente com a conclusão status definida como WINHTTP_CALLBACK_STATUS_SENDREQUEST_COMPLETE. A conclusão do WINHTTP_CALLBACK_STATUS_REQUEST_ERROR indica que a operação foi concluída de forma assíncrona, mas falhou. Ao receber a WINHTTP_CALLBACK_STATUS_SENDREQUEST_COMPLETE status retorno de chamada, o aplicativo pode começar a receber uma resposta do servidor com WinHttpReceiveResponse. Antes disso, nenhuma outra função assíncrona pode ser chamada, caso contrário, ERROR_WINHTTP_INCORRECT_HANDLE_STATE é retornado.

Um aplicativo não deve excluir ou alterar o buffer apontado por lpOptional até que o identificador de solicitação seja fechado ou a chamada para WinHttpReceiveResponse tenha sido concluída, pois um desafio ou redirecionamento de autenticação que exigia os dados opcionais poderia ser encontrado no curso do recebimento da resposta. Se a operação precisar ser anulada com WinHttpCloseHandle, o aplicativo deverá manter o buffer válido até receber o retorno de chamada WINHTTP_CALLBACK_STATUS_REQUEST_ERROR com um código de erro ERROR_WINHTTP_OPERATION_CANCELLED .

Se WinHTTP for usado de forma síncrona, ou seja, quando WINHTP_FLAG_ASYNC não foi definido no WinHttpOpen, um aplicativo não será chamado com uma conclusão status mesmo se uma função de retorno de chamada for registrada. Nesse modo, o aplicativo pode chamar WinHttpReceiveResponse quando WinHttpSendRequest retornar.

A função WinHttpSendRequest envia a solicitação especificada para o servidor HTTP e permite que o cliente especifique cabeçalhos adicionais para enviar junto com a solicitação.

Essa função também permite que o cliente especifique dados opcionais para enviar ao servidor HTTP imediatamente após os cabeçalhos de solicitação. Esse recurso geralmente é usado para operações de gravação, como PUT e POST.

Um aplicativo pode usar o mesmo identificador de solicitação HTTP em várias chamadas para WinHttpSendRequest para enviar novamente a mesma solicitação, mas o aplicativo deve ler todos os dados retornados da chamada anterior antes de chamar essa função novamente.

O nome e o valor dos cabeçalhos de solicitação adicionados com essa função são validados. Os cabeçalhos devem estar bem formados. Para obter mais informações sobre cabeçalhos HTTP válidos, consulte RFC 2616. Se um cabeçalho inválido for usado, essa função falhará e GetLastErrorretornará ERROR_INVALID_PARAMETER. O cabeçalho inválido não é adicionado.

Windows 2000: Ao enviar solicitações de vários threads, pode haver uma diminuição significativa no desempenho da rede e da CPU.

Windows XP e Windows 2000: Consulte Requisitos de tempo de execução.

WinHttpSetStatusCallback

Se uma função de retorno de chamada status tiver sido instalada com WinHttpSetStatusCallback, as seguintes notificações que foram definidas no parâmetro dwNotificationFlags de WinHttpSetStatusCallback indicam o progresso no envio da solicitação:
  • WINHTTP_CALLBACK_STATUS_DETECTING_PROXY (não implementado)
  • WINHTTP_CALLBACK_STATUS_SENDREQUEST_COMPLETE (somente no modo assíncrono)
  • WINHTTP_CALLBACK_STATUS_REDIRECT
  • WINHTTP_CALLBACK_STATUS_SECURE_FAILURE
  • WINHTTP_CALLBACK_STATUS_INTERMEDIATE_RESPONSE
Nota No Windows 7 e no Windows Server 2008 R2, todas as notificações a seguir foram preteridas.
 
  • WINHTTP_CALLBACK_STATUS_RESOLVING_NAME
  • WINHTTP_CALLBACK_STATUS_NAME_RESOLVED
  • WINHTTP_CALLBACK_STATUS_CONNECTING_TO_SERVER
  • WINHTTP_CALLBACK_STATUS_CONNECTED_TO_SERVER
  • WINHTTP_CALLBACK_STATUS_SENDING_REQUEST
  • WINHTTP_CALLBACK_STATUS_REQUEST_SENT
  • WINHTTP_CALLBACK_STATUS_RECEIVING_RESPONSE
  • WINHTTP_CALLBACK_STATUS_RESPONSE_RECEIVED
Se o servidor fechar a conexão, as seguintes notificações também serão enviadas, desde que tenham sido definidas no parâmetro dwNotificationFlags de WinHttpSetStatusCallback:
  • WINHTTP_CALLBACK_STATUS_CLOSING_CONNECTION
  • WINHTTP_CALLBACK_STATUS_CONNECTION_CLOSED

Suporte para carregamento maior que 4 GB

A partir do Windows Vista e do Windows Server 2008, o WinHttp dá suporte ao carregamento de arquivos até o tamanho de um LARGE_INTEGER (2^64 bytes) usando o cabeçalho Comprimento do Conteúdo. Os comprimentos de carga especificados na chamada para WinHttpSendRequest são limitados ao tamanho de um DWORD (2^32 bytes). Para carregar dados em uma URL maior que um DWORD, o aplicativo deve fornecer o comprimento no cabeçalho Comprimento do Conteúdo da solicitação. Nesse caso, o aplicativo cliente WinHttp chama WinHttpSendRequest com o parâmetro dwTotalLength definido como WINHTTP_IGNORE_REQUEST_TOTAL_LENGTH.

Se o cabeçalho Comprimento do Conteúdo especificar um comprimento menor que 2^32, o aplicativo também deverá especificar o comprimento do conteúdo na chamada para WinHttpSendRequest. Se o parâmetro dwTotalLength não corresponder ao comprimento especificado no cabeçalho Content-Length, a chamada falhará e retornará ERROR_INVALID_PARAMETER.

O cabeçalho Content-Length pode ser adicionado na chamada a WinHttpAddRequestHeaders ou pode ser especificado no parâmetro lpszHeader de WinHttpSendRequest , conforme mostrado no exemplo de código a seguir.

BOOL fRet = WinHttpSendRequest(
			hReq,
			L"Content-Length: 68719476735\r\n",
			-1L,
			WINHTTP_NO_REQUEST_DATA,
			0,
			WINHTTP_IGNORE_REQUEST_TOTAL_LENGTH,
			pMyContent);

Cabeçalho transfer-encoding

A partir do Windows Vista e do Windows Server 2008, o WinHttp permite que os aplicativos executem a codificação de transferência em partes nos dados enviados ao servidor. Quando o cabeçalho Transfer-Encoding estiver presente na solicitação WinHttp, o parâmetro dwTotalLength na chamada para WinHttpSendRequest será definido como WINHTTP_IGNORE_REQUEST_TOTAL_LENGTH e o aplicativo enviará o corpo da entidade em uma ou mais chamadas para WinHttpWriteData. O parâmetro lpOptional de WinHttpSendRequest deve ser NULL e o parâmetro dwOptionLength deve ser zero, caso contrário, um erro de ERROR_WINHTTP_INVALID_PARAMETER é retornado. Para encerrar a transferência de dados em partes, o aplicativo gera uma parte de comprimento zero e a envia na última chamada para WinHttpWriteData.

Exemplos

O exemplo de código a seguir mostra como obter um identificador HINTERNET , abrir uma sessão HTTP, criar um cabeçalho de solicitação e enviar esse cabeçalho para o servidor.

    BOOL  bResults = FALSE;
    HINTERNET hSession = NULL,
              hConnect = NULL,
              hRequest = NULL;

    // Use WinHttpOpen to obtain a session handle.
    hSession = WinHttpOpen(  L"A WinHTTP Example Program/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"www.wingtiptoys.com",
                                   INTERNET_DEFAULT_HTTP_PORT, 0);

    // Create an HTTP Request handle.
    if (hConnect)
        hRequest = WinHttpOpenRequest( hConnect, L"PUT", 
                                       L"/writetst.txt", 
                                       NULL, WINHTTP_NO_REFERER, 
                                       WINHTTP_DEFAULT_ACCEPT_TYPES, 
                                       0);

    // Send a Request.
    if (hRequest) 
        bResults = WinHttpSendRequest( hRequest, 
                                       WINHTTP_NO_ADDITIONAL_HEADERS,
                                       0, WINHTTP_NO_REQUEST_DATA, 0, 
                                       0, 0);

    // Place additional code here.


    // Report errors.
    if (!bResults)
        printf("Error %d has occurred.\n",GetLastError());

    // Close open handles.
    if (hRequest) WinHttpCloseHandle(hRequest);
    if (hConnect) WinHttpCloseHandle(hConnect);
    if (hSession) WinHttpCloseHandle(hSession);

Requisitos

Requisito Valor
Cliente mínimo com suporte Windows XP, Windows 2000 Professional com SP3 [somente aplicativos da área de trabalho]
Servidor mínimo com suporte Windows Server 2003, Windows 2000 Server com SP3 [somente aplicativos da área de trabalho]
Plataforma de Destino Windows
Cabeçalho winhttp.h
Biblioteca Winhttp.lib
DLL Winhttp.dll
Redistribuível WinHTTP 5.0 e Internet Explorer 5.01 ou posterior no Windows XP e Windows 2000.

Confira também

Sobre os Serviços HTTP do Microsoft Windows (WinHTTP)

WINHTTP_STATUS_CALLBACK

Versões do WinHTTP

WinHttpCloseHandle

WinHttpConnect

WinHttpOpen

WinHttpOpenRequest

WinHttpReceiveResponse