Purpose: Windows HTTP and WebSockets API Libraries
- this unit is a part of the Open Source Synopse mORMot framework 2, licensed under a MPL/GPL/LGPL three license - see LICENSE.md
Unit Name | Description | |
---|---|---|
mormot.core.base | Framework Core Shared Types and RTL-like Functions | |
mormot.core.os | Framework Core Low-Level Wrappers to the Operating-System API | |
mormot.core.text | Framework Core Low-Level Text Processing | |
mormot.core.unicode | Framework Core Low-Level Unicode UTF-8 UTF-16 Ansi Conversion | |
mormot.net.http | HTTP/HTTPS Abstract Process Classes and Definitions | |
mormot.net.sock | Low-level access to the OperatingSystem Sockets API (e.g. WinSock2) |
Objects | Description | |
---|---|---|
EHttpApiServer | Exception raised during http.sys HTTP/1.1 process | |
EWebSocketApi | Exception raised during http.sys WebSockets process | |
HTTP_DATA_CHUNK_INMEMORY | We use 3 distinct HTTP_DATA_CHUNK_* records since variable records alignment is buggy/non compatible under Delphi XE3 | |
HTTP_REQUEST | Structure used to handle data associated with a specific request | |
HTTP_RESPONSE | Structure as expected by HttpSendHttpResponse() API | |
HTTP_VERSION | HTTP version used | |
THttpApi | Direct late-binding access to the HTTP API server 1.0 or 2.0 | |
TProxyInfo | Proxy information as returned by GetProxyInfo() | |
TWebSocketApi | Direct late-binding access to the WebSocket Protocol Component API functions | |
TWinHttpBinding | Direct late-binding access to the WinHttp API |
HTTP_VERSION = packed record
HTTP
version used
HTTP_DATA_CHUNK_INMEMORY = record
We use 3 distinct HTTP_DATA_CHUNK_* records since variable records alignment is buggy/non compatible under Delphi XE3
Reserved1: ULONG;
Always hctFromMemory
HTTP_REQUEST = record
Structure used to handle data associated with a specific request
Address: HTTP_TRANSPORT_ADDRESS;
Local and remote transport addresses for the connection
BytesReceived: ULONGLONG;
The total number of bytes received from network for this request
ConnectionId: HTTP_CONNECTION_ID;
An identifier for the connection on which the request was received
CookedUrl: HTTP_COOKED_URL;
The canonicalized Unicode URL
Flags: cardinal;
Either 0 (Only Header), either HTTP_RECEIVE_REQUEST_FLAG_COPY_BODY
Headers: HTTP_REQUEST_HEADERS;
The request headers.
pRawUrl: PAnsiChar;
Pointer to the raw (uncooked) URL
pRequestInfo: PHTTP_REQUEST_INFOS;
V2 trailing structure used to handle extended info about a specific request
pSslInfo: PHTTP_SSL_INFO;
TLS connection information
pUnknownVerb: PAnsiChar;
Pointer to the verb
string if the Verb
field is hvUnknown
RawUrlLength: word;
The length of the raw (uncooked) URL (in bytes not including the last #0)
RequestId: HTTP_REQUEST_ID;
A value used to identify the request when calling HttpReceiveRequestEntityBody, HttpSendHttpResponse, and/or HttpSendResponseEntityBody
RequestInfoCount: word;
How many extended info about a specific request is available in v2
UnknownVerbLength: word;
The length of the verb
string if the Verb
field is hvUnknown (in bytes not including the last #0)
UrlContext: HTTP_URL_CONTEXT;
The context associated with the URL prefix
Verb: THttpVerb;
An HTTP
verb
associated with this request
Version: HTTP_VERSION;
The HTTP
version
number
HTTP_RESPONSE = object(TObject)
Structure as expected by HttpSendHttpResponse() API
EntityChunkCount: word;
Number of elements in pEntityChunks
[] array
Headers: HTTP_RESPONSE_HEADERS;
The response headers
pEntityChunks: pointer;
PEntityChunks
points to an array of EntityChunkCount
HTTP_DATA_CHUNK_*
pReason: PUtf8Char;
The HTTP
reason (e.g., "OK"). This MUST not contain non-ASCII characters (i.e., all chars must be in range 0x20-0x7E).
pResponseInfo: PHTTP_RESPONSE_INFO;
Map the HTTP
API 2.0 extended information
ReasonLength: word;
In bytes not including the '\0'
ResponseInfoCount: word;
Contains the number of HTTP
API 2.0 extended information
StatusCode: word;
The HTTP
status code (e.g., 200)
Version: HTTP_VERSION;
The raw HTTP
protocol version
number
function AddCustomHeader(P: PUtf8Char; var UnknownHeaders: HTTP_UNKNOWN_HEADERS; ForceCustomHeader: boolean): PUtf8Char;
Add one header value to the internal headers
- SetHeaders
() method should have been called before to initialize the internal UnknownHeaders[] array
procedure SetContent(var DataChunk: HTTP_DATA_CHUNK_INMEMORY; const Content: RawByteString; const ContentType: RawUtf8 = 'text/html');
Will set the content of the reponse, and ContentType header
procedure SetHeaders(P: PUtf8Char; var UnknownHeaders: HTTP_UNKNOWN_HEADERS; NoXPoweredHeader: boolean);
Will set all header values from lines
- Content-Type/Content-Encoding/Location will be set in KnownHeaders[]
- all other headers
will be set in temp UnknownHeaders[]
procedure SetStatus(code: integer; var OutStatus: RawUtf8);
Will set both StatusCode
and Reason
- OutStatus is a temporary variable which will be field with the corresponding text
THttpApi = packed record
Direct late-binding access to the HTTP
API server 1.0 or 2.0
AddUrl: function(ReqQueueHandle: THandle; UrlPrefix: PWideChar; Reserved: integer = 0): HRESULT; stdcall;
The HttpAddUrl function registers a given URL so that requests that match it are routed to a specified HTTP
Server API request queue. An application can register multiple URLs to a single request queue using repeated calls to HttpAddUrl
- a typical url prefix is 'http
://+:80/vroot/', 'https://+:80/vroot/' or 'https://adatum.com:443/secure/database/' - here the '+' is called a Strong wildcard, i.e. will match every IP or server name
AddUrlToUrlGroup: function(UrlGroupId: HTTP_URL_GROUP_ID; pFullyQualifiedUrl: PWideChar; UrlContext: HTTP_URL_CONTEXT = 0; Reserved: ULONG = 0): HRESULT; stdcall;
Adds the specified URL to the URL Group identified by the URL Group ID
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
- this function replaces the HTTP
version
1.0 AddUrl
() function
CancelHttpRequest: function(ReqQueueHandle: THandle; RequestId: HTTP_REQUEST_ID; pOverlapped: pointer = nil): HRESULT; stdcall;
Cancels a specified request
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
CloseServerSession: function(ServerSessionId: HTTP_SERVER_SESSION_ID): HRESULT; stdcall;
Deletes the server session identified by the server session ID
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
CloseUrlGroup: function(UrlGroupId: HTTP_URL_GROUP_ID): HRESULT; stdcall;
Closes the URL Group identified by the URL Group ID
- this call also removes all of the URLs that are associated with the URL Group
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
CreateHttpHandle: function(var ReqQueueHandle: THandle; Reserved: integer = 0): HRESULT; stdcall;
The HttpCreateHttpHandle function creates an HTTP
request queue for the calling application and returns a handle to it.
CreateRequestQueue: function(Version: HTTP_VERSION; pName: PWideChar; pSecurityAttributes: pointer; Flags: ULONG; var ReqQueueHandle: THandle): HRESULT; stdcall;
Creates a new request queue or opens an existing request queue
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
- replaces the HTTP
version
1.0 CreateHttpHandle
() function
CreateServerSession: function(Version: HTTP_VERSION; var ServerSessionId: HTTP_SERVER_SESSION_ID; Reserved: ULONG = 0): HRESULT; stdcall;
Creates a server session for the specified HTTP
API version
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
CreateUrlGroup: function(ServerSessionId: HTTP_SERVER_SESSION_ID; var UrlGroupId: HTTP_URL_GROUP_ID; Reserved: ULONG = 0): HRESULT; stdcall;
Creates a URL Group under the specified server session
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
DeleteServiceConfiguration: function(ServiceHandle: THandle; ConfigId: THttpServiceConfigID; pConfigInformation: pointer; ConfigInformationLength: ULONG; pOverlapped: pointer = nil): HRESULT; stdcall;
Deletes specified data, such as IP addresses or TLS Certificates, from the HTTP
Server API configuration store
FlushResponseCache: function(ReqQueueHandle: THandle; pUrlPrefix: PWideChar; Flags: ULONG; pOverlapped: POverlapped): ULONG; stdcall;
Removes from the HTTP
Server API cache associated with a given request queue all response fragments that have a name whose site portion matches a specified UrlPrefix
Initialize: function(Version: HTTP_VERSION; Flags: cardinal; pReserved: pointer = nil): HRESULT; stdcall;
The HttpInitialize function initializes the HTTP
Server API driver, starts it, if it has not already been started, and allocates data structures for the calling application to support response-queue creation and other operations. Call this function before calling any other functions in the HTTP
Server API.
Module: THandle;
Access to the httpapi.dll loaded library
QueryRequestQueueProperty: function(ReqQueueHandle: THandle; aProperty: HTTP_SERVER_PROPERTY; pPropertyInformation: pointer; PropertyInformationLength: ULONG; Reserved: ULONG; pReturnLength: PULONG; pReserved: pointer): HRESULT; stdcall;
Queries a property of the request queue identified by the specified handle
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
QueryServerSessionProperty: function(ServerSessionId: HTTP_SERVER_SESSION_ID; aProperty: HTTP_SERVER_PROPERTY; pPropertyInformation: pointer; PropertyInformationLength: ULONG; pReturnLength: PULONG = nil): HRESULT; stdcall;
Queries a server property on the specified server session
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
QueryUrlGroupProperty: function(UrlGroupId: HTTP_URL_GROUP_ID; aProperty: HTTP_SERVER_PROPERTY; pPropertyInformation: pointer; PropertyInformationLength: ULONG; pReturnLength: PULONG = nil): HRESULT; stdcall;
Queries a property on the specified URL Group
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
ReceiveHttpRequest: function(ReqQueueHandle: THandle; RequestId: HTTP_REQUEST_ID; Flags: cardinal; var pRequestBuffer: HTTP_REQUEST; RequestBufferLength: ULONG; var pBytesReceived: ULONG; pOverlapped: pointer = nil): HRESULT; stdcall;
Retrieves the next available HTTP
request from the specified request queue
ReceiveRequestEntityBody: function(ReqQueueHandle: THandle; RequestId: HTTP_REQUEST_ID; Flags: ULONG; pBuffer: pointer; BufferLength: cardinal; var pBytesReceived: cardinal; pOverlapped: pointer = nil): HRESULT; stdcall;
Receives additional entity body data for a specified HTTP
request
RemoveUrl: function(ReqQueueHandle: THandle; UrlPrefix: PWideChar): HRESULT; stdcall;
Unregisters a specified URL, so that requests for it are no longer routed to a specified queue.
RemoveUrlFromUrlGroup: function(UrlGroupId: HTTP_URL_GROUP_ID; pFullyQualifiedUrl: PWideChar; Flags: ULONG): HRESULT; stdcall;
Removes the specified URL from the group identified by the URL Group ID
- this function removes one, or all, of the URLs from the group
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
- it replaces the HTTP
version
1.0 RemoveUrl
() function
SendHttpResponse: function(ReqQueueHandle: THandle; RequestId: HTTP_REQUEST_ID; Flags: integer; var pHttpResponse: HTTP_RESPONSE; pReserved1: pointer; var pBytesSent: cardinal; pReserved2: pointer = nil; Reserved3: ULONG = 0; pOverlapped: pointer = nil; pLogData: PHTTP_LOG_DATA = nil): HRESULT; stdcall;
Sent the response to a specified HTTP
request
- pLogData optional parameter is handled since HTTP
API 2.0
SendResponseEntityBody: function(ReqQueueHandle: THandle; RequestId: HTTP_REQUEST_ID; Flags: integer; EntityChunkCount: word; pEntityChunks: pointer; var pBytesSent: cardinal; pReserved1: pointer = nil; pReserved2: pointer = nil; pOverlapped: POverlapped = nil; pLogData: PHTTP_LOG_DATA = nil): HRESULT; stdcall;
Sends entity-body data associated with an HTTP
response.
SetRequestQueueProperty: function(ReqQueueHandle: THandle; aProperty: HTTP_SERVER_PROPERTY; pPropertyInformation: pointer; PropertyInformationLength: ULONG; Reserved: ULONG; pReserved: pointer): HRESULT; stdcall;
Sets a new property or modifies an existing property on the request queue identified by the specified handle
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
SetServerSessionProperty: function(ServerSessionId: HTTP_SERVER_SESSION_ID; aProperty: HTTP_SERVER_PROPERTY; pPropertyInformation: pointer; PropertyInformationLength: ULONG): HRESULT; stdcall;
Sets a new server session property or modifies an existing property on the specified server session
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
SetServiceConfiguration: function(ServiceHandle: THandle; ConfigId: THttpServiceConfigID; pConfigInformation: pointer; ConfigInformationLength: ULONG; pOverlapped: pointer = nil): HRESULT; stdcall;
Set specified data, such as IP addresses or TLS Certificates, from the HTTP
Server API configuration store
SetUrlGroupProperty: function(UrlGroupId: HTTP_URL_GROUP_ID; aProperty: HTTP_SERVER_PROPERTY; pPropertyInformation: pointer; PropertyInformationLength: ULONG): HRESULT; stdcall;
Sets a new property or modifies an existing property on the specified URL Group
- available only for HTTP
API 2.0 (since Windows Vista / Server 2008)
Terminate: function(Flags: cardinal; Reserved: integer = 0): HRESULT; stdcall;
The HttpTerminate function cleans up resources used by the HTTP
Server API to process calls by an application. An application should call HttpTerminate once for every time it called HttpInitialize, with matching flag settings.
Version: HTTP_VERSION;
Will be either 1.0 or 2.0, depending on the published .dll functions
EHttpApiServer = class(ESynException)
Exception raised during http.sys HTTP
/1.1 process
constructor Create(api: THttpApis; Error: integer); reintroduce;
Initialize a new EHttpApiServer
instance
class procedure RaiseOnError(api: THttpApis; Error: integer);
Raise an EHttpApiServer
if the http.sys API result code is an error
property LastApi: THttpApis read fLastApi;
The execution context of this exception
property LastApiError: integer read fLastApiError;
The error code of this exception
TWinHttpBinding = packed record
Direct late-binding access to the WinHttp API
- note: WebSocket* API calls require Windows 8 and later
AddRequestHeaders: function(hRequest: HINTERNET; pwszHeaders: PWideChar; dwHeadersLength: DWORD; dwModifiers: DWORD): BOOL; stdcall;
Adds one or more HTTP
request headers to the HTTP
request handle.
CloseHandle: function(hInternet: HINTERNET): BOOL; stdcall;
Closes a single HINTERNET
handle.
Connect: function(hSession: HINTERNET; pswzServerName: PWideChar; nServerPort: INTERNET_PORT; dwReserved: DWORD): HINTERNET; stdcall;
Specifies the initial target server of an HTTP
request.
GetIEProxyConfigForCurrentUser: function( var pProxyInfo: WINHTTP_CURRENT_USER_IE_PROXY_CONFIG): BOOL; stdcall;
Retrievs the Internet Explorer Proxy information.
GetProxyForUrl: function(hSession: HINTERNET; lpcwszUrl: LPCWSTR; pAutoProxyOptions: PWINHTTP_AUTOPROXY_OPTIONS; var pProxyInfo: WINHTTP_PROXY_INFO): BOOL; stdcall;
Retrieves the low-level Proxy information for a given URI.
LibraryHandle: THandle;
Access to the winhttp.dll loaded library
Open: function(pwszUserAgent: PWideChar; dwAccessType: DWORD; pwszProxyName, pwszProxyBypass: PWideChar; dwFlags: DWORD): HINTERNET; stdcall;
Initializes an application's use of the WinHttp functions.
OpenRequest: function(hConnect: HINTERNET; pwszVerb: PWideChar; pwszObjectName: PWideChar; pwszVersion: PWideChar; pwszReferer: PWideChar; ppwszAcceptTypes: PLPWSTR; dwFlags: DWORD): HINTERNET; stdcall;
Creates an HTTP
request handle.
QueryDataAvailable: function(hRequest: HINTERNET; var lpdwNumberOfBytesAvailable: DWORD): BOOL; stdcall;
Returns the amount of data, in bytes, available to be read with WinHttpReadData.
QueryHeaders: function(hRequest: HINTERNET; dwInfoLevel: DWORD; pwszName: PWideChar; lpBuffer: pointer; var lpdwBufferLength, lpdwIndex: DWORD): BOOL; stdcall;
Retrieves header information associated with an HTTP
request.
QueryOption: function(hInet: HINTERNET; dwOption: DWORD; lpBuffer: pointer; var lpdwBufferLength: DWORD): BOOL; stdcall;
Retrieves some options about the current connection.
ReadData: function(hRequest: HINTERNET; lpBuffer: pointer; dwNumberOfBytesToRead: DWORD; var lpdwNumberOfBytesRead: DWORD): BOOL; stdcall;
Reads data from a handle opened by the WinHttpOpenRequest function.
ReceiveResponse: function(hRequest: HINTERNET; lpReserved: pointer): BOOL; stdcall;
Ends an HTTP
request that is initiated by WinHttpSendRequest.
SendRequest: function(hRequest: HINTERNET; pwszHeaders: PWideChar; dwHeadersLength: DWORD; lpOptional: pointer; dwOptionalLength: DWORD; dwTotalLength: DWORD; dwContext: DWORD): BOOL; stdcall;
Sends the specified request to the HTTP
server.
SetCredentials: function(hRequest: HINTERNET; AuthTargets: DWORD; AuthScheme: DWORD; pwszUserName: PWideChar; pwszPassword: PWideChar; pAuthParams: pointer): BOOL; stdcall;
Passes the required authorization credentials to the server.
SetOption: function(hInternet: HINTERNET; dwOption: DWORD; lpBuffer: pointer; dwBufferLength: DWORD): BOOL; stdcall;
Sets an Internet option.
SetStatusCallback: function(hSession: HINTERNET; lpfnInternetCallback: WINHTTP_STATUS_CALLBACK; dwNotificationFlags: DWORD; dwReserved: PDWORD): WINHTTP_STATUS_CALLBACK; stdcall;
Sets up a callback function that WinHttp can call as progress is made during an operation.
SetTimeouts: function(hInternet: HINTERNET; dwResolveTimeout: DWORD; dwConnectTimeout: DWORD; dwSendTimeout: DWORD; dwReceiveTimeout: DWORD): BOOL; stdcall;
Sets the various time-outs that are involved with HTTP
transactions.
WebSocketClose: function(hWebSocket: HINTERNET; usStatus: Word; pvReason: pointer; dwReasonLength: DWORD): DWORD; stdcall;
Closes a WebSocket connection.
WebSocketCompleteUpgrade: function(hRequest: HINTERNET; lpReserved: pointer): HINTERNET; stdcall;
Completes a WebSocket handshake started by WinHttpSendRequest.
WebSocketEnabled: boolean;
Depends on the published .dll functions
WebSocketQueryCloseStatus: function(hWebSocket: HINTERNET; out usStatus: Word; pvReason: pointer; dwReasonLength: DWORD; out dwReasonLengthConsumed: DWORD): DWORD; stdcall;
Retrieves the close status sent by a server
WebSocketReceive: function(hWebSocket: HINTERNET; pvBuffer: pointer; dwBufferLength: DWORD; out dwBytesRead: DWORD; out eBufferType: WINHTTP_WEB_SOCKET_BUFFER_TYPE): DWORD; stdcall;
Receives data from a WebSocket connection.
WebSocketSend: function(hWebSocket: HINTERNET; eBufferType: WINHTTP_WEB_SOCKET_BUFFER_TYPE; pvBuffer: pointer; dwBufferLength: DWORD): DWORD; stdcall;
Sends data over a WebSocket connection.
WriteData: function(hRequest: HINTERNET; lpBuffer: pointer; dwNumberOfBytesToWrite: DWORD; var lpdwNumberOfBytesWritten: DWORD): BOOL; stdcall;
Writes data to a handle opened by the WinHttpOpenRequest function.
TProxyInfo = record
Proxy information as returned by GetProxyInfo()
AutoDetected: Boolean;
If the Proxy settings were auto-detected by Internet Explorer
Bypass: SynUnicode;
The Bypass
rule
ErrorMessage: RawUtf8;
Detailed error message, if GetProxyInfo() returned a non 0 error code
URL: SynUnicode;
The proxy server address and port, e.g. '10.0.0.8:7985'
TWebSocketApi = packed record
Direct late-binding access to the WebSocket Protocol Component API functions
AbortHandle: procedure(hWebSocket: WEB_SOCKET_HANDLE); stdcall;
Aborts a WebSocket session handle created by WebSocketCreateClientHandle or WebSocketCreateServerHandle
BeginClientHandshake: function(hWebSocket: WEB_SOCKET_HANDLE; pszSubprotocols: PAnsiChar; ulSubprotocolCount: ULONG; pszExtensions: PAnsiChar; ulExtensionCount: ULONG; const pInitialHeaders: PWEB_SOCKET_HTTP_HEADER; ulInitialHeaderCount: ULONG; out pAdditionalHeaders: PWEB_SOCKET_HTTP_HEADER; out pulAdditionalHeaderCount: ULONG): HRESULT; stdcall;
Begins the client-side handshake
BeginServerHandshake: function(hWebSocket: WEB_SOCKET_HANDLE; pszSubprotocolSelected: PAnsiChar; pszExtensionSelected: PAnsiChar; ulExtensionSelectedCount: ULONG; const pRequestHeaders: PWEB_SOCKET_HTTP_HEADER; ulRequestHeaderCount: ULONG; out pResponseHeaders: PWEB_SOCKET_HTTP_HEADER; out pulResponseHeaderCount: ULONG): HRESULT; stdcall;
Begins the server-side handshake
CompleteAction: function(hWebSocket: WEB_SOCKET_HANDLE; pvActionContext: pointer; ulBytesTransferred: ULONG): HRESULT; stdcall;
Completes an action started by WebSocketGetAction
CreateClientHandle: function(const pProperties: PWEB_SOCKET_PROPERTY; ulPropertyCount: ULONG; out phWebSocket: WEB_SOCKET_HANDLE): HRESULT; stdcall;
Creates a client-side WebSocket session handle
CreateServerHandle: function(const pProperties: PWEB_SOCKET_PROPERTY; ulPropertyCount: ULONG; out phWebSocket: WEB_SOCKET_HANDLE): HRESULT; stdcall;
Creates a server-side WebSocket session handle
DeleteHandle: procedure(hWebSocket: WEB_SOCKET_HANDLE); stdcall;
Deletes a WebSocket session handle created by WebSocketCreateClientHandle or WebSocketCreateServerHandle
EndClientHandshake: function(hWebSocket: WEB_SOCKET_HANDLE; const pResponseHeaders: PWEB_SOCKET_HTTP_HEADER; ulReponseHeaderCount: ULONG; var pulSelectedExtensions: ULONG; var pulSelectedExtensionCount: ULONG; var pulSelectedSubprotocol: ULONG): HRESULT; stdcall;
Completes the client-side handshake
EndServerHandshake: function(hWebSocket: WEB_SOCKET_HANDLE): HRESULT; stdcall;
Completes the server-side handshake
GetAction: function(hWebSocket: WEB_SOCKET_HANDLE; eActionQueue: WEB_SOCKET_ACTION_QUEUE; pDataBuffers: pointer ; var pulDataBufferCount: ULONG; var pAction: WEB_SOCKET_ACTION; var pBufferType: WEB_SOCKET_BUFFER_TYPE; var pvApplicationContext: pointer; var pvActionContext: pointer): HRESULT; stdcall;
Returns an action from a call to WebSocketSend, WebSocketReceive or WebSocketCompleteAction
GetGlobalProperty: function(eType: WEB_SOCKET_PROPERTY_TYPE; pvValue: pointer; var ulSize: ULONG): HRESULT; stdcall;
Gets a single WebSocket property
LibraryHandle: THandle;
Acces to the loaded library handle
Receive: function(hWebSocket: WEB_SOCKET_HANDLE; pBuffer: pointer; pvContext: pointer): HRESULT; stdcall;
Adds a receive
operation to the protocol component operation queue
Send: function(hWebSocket: WEB_SOCKET_HANDLE; BufferType: WEB_SOCKET_BUFFER_TYPE; pBuffer, Context: pointer): HRESULT; stdcall;
Adds a send operation to the protocol component operation queue
WebSocketEnabled: boolean;
Depends on Windows version
EWebSocketApi = class(ESynException)
Exception raised during http.sys WebSockets process
constructor Create(api: TWebSocketApis; Error: integer); reintroduce; overload;
Initialize a new EWebSocketApi
instance
class procedure RaiseOnError(api: TWebSocketApis; Error: integer);
Raise an EWebSocketApi
if the http.sys API result code is an error
property LastApi: TWebSocketApis read fLastApi;
The execution context of this exception
property LastError: integer read fLastError;
The error code of this exception
HTTP_AUTH_STATUS = ( HttpAuthStatusSuccess, HttpAuthStatusNotAuthenticated, HttpAuthStatusFailure );
About Authentication in HTTP
Version 2.0 see https://msdn.microsoft.com/en-us/library/windows/desktop/aa364452
PHTTP_QOS_SETTING_TYPE = ^HTTP_QOS_SETTING_TYPE;
Windows Server 2008 R2 and Windows 7 only
PWINHTTP_PROXY_INFO = ^WINHTTP_PROXY_INFO;
Proxy bypass list
THttpApiLogFields = set of ( hlfDate, hlfTime, hlfClientIP, hlfUserName, hlfSiteName, hlfComputerName, hlfServerIP, hlfMethod, hlfUriStem, hlfUriQuery, hlfStatus, hlfWIN32Status, hlfBytesSent, hlfBytesRecv, hlfTimeTaken, hlfServerPort, hlfUserAgent, hlfCookie, hlfReferer, hlfVersion, hlfHost, hlfSubStatus);
Http.sys API 2.0 fields used for W3C logging
- match low-level HTTP_LOG_FIELD_* constants as defined in HTTP
2.0 API
THttpApiLoggingFlags = set of ( hlfLocalTimeRollover, hlfUseUtf8Conversion, hlfLogErrorsOnly, hlfLogSuccessOnly);
Http.sys API 2.0 logging option flags
- used to alter the default logging behavior
- hlfLocalTimeRollover would force the log file rollovers by local time, instead of the default GMT time
- hlfUseUtf8Conversion will use UTF-8 instead of default local code page
- only one of hlfLogErrorsOnly and hlfLogSuccessOnly flag could be set at a time: if neither of them are present, both errors and success will be logged, otherwise mutually exclusive flags could be set to force only errors or success logging
- match low-level HTTP_LOGGING_FLAG_* constants as defined in HTTP
2.0 API
THttpApiLoggingRollOver = ( hlrSize, hlrDaily, hlrWeekly, hlrMonthly, hlrHourly );
Http.sys API 2.0 logging file rollover types
- match low-level HTTP_LOGGING_ROLLOVER_TYPE
as defined in HTTP
2.0 API
THttpApiLoggingType = ( hltW3C, hltIIS, hltNCSA, hltRaw );
Http.sys API 2.0 logging file supported layouts
- match low-level HTTP_LOGGING_TYPE
as defined in HTTP
2.0 API
THttpApiRequestAuthentications = set of ( haBasic, haDigest, haNtlm, haNegotiate, haKerberos);
Http.sys API 2.0 fields used for server-side authentication
- as used by THttpApiServer.SetAuthenticationSchemes
/AuthenticationSchemes
- match low-level HTTP_AUTH_ENABLE_* constants as defined in HTTP
2.0 API
THttpHeader = ( reqCacheControl, reqConnection, reqDate, reqKeepAlive, reqPragma, reqTrailer, reqTransferEncoding, reqUpgrade, reqVia, reqWarning, reqAllow, reqContentLength, reqContentType, reqContentEncoding, reqContentLanguage, reqContentLocation, reqContentMd5, reqContentRange, reqExpires, reqLastModified, reqAccept, reqAcceptCharset, reqAcceptEncoding, reqAcceptLanguage, reqAuthorization, reqCookie, reqExpect, reqFrom, reqHost, reqIfMatch, reqIfModifiedSince, reqIfNoneMatch, reqIfRange, reqIfUnmodifiedSince, reqMaxForwards, reqProxyAuthorization, reqReferrer, reqRange, reqTe, reqTranslate, reqUserAgent, respAcceptRanges, respAge, respEtag, respLocation, respProxyAuthenticate, respRetryAfter, respServer, respSetCookie, respVary, respWwwAuthenticate );
The req* values identify Request Headers, and resp* Response Headers
TWebSocketApis = ( hAbortHandle, hBeginClientHandshake, hBeginServerHandshake, hCompleteAction, hCreateClientHandle, hCreateServerHandle, hDeleteHandle, hEndClientHandshake, hEndServerHandshake, hGetAction, hGetGlobalProperty, hReceive, hSend );
Identify each TWebSocketApi
late-binding API function
WEB_SOCKET_BUFFER_TYPE = ULONG;
The bit values used to construct the WebSocket frame header for httpapi.dll
- not equals to WINHTTP_WEB_SOCKET_BUFFER_TYPE
from winhttp.dll
WEB_SOCKET_CLOSE_STATUS = Word;
WebSocket close status as defined by http
://tools.ietf.org/html/rfc6455#section-7.4
WEB_SOCKET_HANDLE = pointer;
Low-level API reference to a WebSocket session
WINHTTP_WEB_SOCKET_BUFFER_TYPE = ULONG;
Types of WebSocket buffers for winhttp.dll it is the different thing than WEB_SOCKET_BUFFER_TYPE
for httpapi.dll
HTTPAPI_DLL = 'httpapi.dll';
The name of the Windows http.sys API library
HTTPAPI_ERROR_NONEXISTENTCONNECTION = 1229;
Error raised by HTTP
API when the client disconnected (e.g. after timeout)
HTTP_INITIALIZE_CONFIG = 2;
Initialization for applications that use the HTTP
configuration functions
HTTP_INITIALIZE_SERVER = 1;
Initialization for applications that use the HTTP
Server API
HTTP_LOGGING_FLAG_LOCAL_TIME_ROLLOVER = 1;
HTTP_LOGGING_FLAG_LOCAL_TIME_ROLLOVER
- This flag is used to change the log file rollover to happen by local time based. By default log file rollovers happen by GMT time.
HTTP_LOGGING_FLAG_LOG_ERRORS_ONLY = 4;
HTTP_LOGGING_FLAG_LOG_ERRORS_ONLY
- HTTP_LOGGING_FLAG_LOG_SUCCESS_ONLY
- These two flags are used to to do selective logging. If neither of them are present both types of requests will be logged. Only one these flags can be set at a time. They are mutually exclusive.
HTTP_LOGGING_FLAG_USE_UTF8_CONVERSION = 2;
HTTP_LOGGING_FLAG_USE_UTF8_CONVERSION
- When set the unicode fields will be converted to UTF-8 multibytes when writing to the log files. When this flag is not present, the local code page conversion happens.
HTTP_LOG_FIELD_CLIENT_PORT = $00400000;
Fields that are used only for error logging
HTTP_LOG_FIELD_DATE = $00000001;
The known log fields recognized/supported by HTTPAPI. Following fields are used for W3C logging. Subset of them are also used for error logging
HTTP_RECEIVE_REQUEST_ENTITY_BODY_FLAG_FILL_BUFFER = 1;
See http
://msdn.microsoft.com/en-us/library/windows/desktop/aa364496
HTTP_RECEIVE_REQUEST_FLAG_COPY_BODY = 1;
If set, available entity body is copied along with the request headers into pEntityChunks
HTTP_REQUEST_FLAG_HTTP2 = 4;
Request was received over HTTP
/2
HTTP_REQUEST_FLAG_IP_ROUTED = 2;
Request was routed based on host and IP binding
HTTP_REQUEST_FLAG_MORE_ENTITY_BODY_EXISTS = 1;
There is more entity body to be read for this request
HTTP_SEND_RESPONSE_FLAG_DISCONNECT = $00000001;
See http
://msdn.microsoft.com/en-us/library/windows/desktop/aa364499
HTTP_URL_FLAG_REMOVE_ALL = 1;
Flag which can be used by HttpRemoveUrlFromUrlGroup()
SECURITY_FLAG_IGNORE_CERTIFICATES: DWORD = SECURITY_FLAG_IGNORE_UNKNOWN_CA or SECURITY_FLAG_IGNORE_CERT_WRONG_USAGE or SECURITY_FLAG_IGNORE_CERT_CN_INVALID or SECURITY_FLAG_IGNORE_CERT_DATE_INVALID;
SECURITY_FLAG_IGNORE_CERT_DATE_INVALID = $00002000;
SECURITY_FLAG_IGNORE_UNKNOWN_CA = $00000100;
Values for WINHTTP_OPTION_SECURITY_FLAGS
WEB_SOCKET_ABORTED_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1006;
The connection was closed without sending or receiving a close frame
WEB_SOCKET_BINARY_FRAGMENT_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000003;
The buffer contains part of a binary message
WEB_SOCKET_BINARY_MESSAGE_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000002;
The buffer contains the last, and possibly only, part of a binary message
WEB_SOCKET_CLOSE_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000004;
The buffer contains a close message
WEB_SOCKET_EMPTY_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1005;
No close status code was provided
WEB_SOCKET_ENDPOINT_UNAVAILABLE_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1001;
The endpoint is going away and thus closing the connection
WEB_SOCKET_INVALID_DATA_TYPE_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1003;
The endpoint cannot receive this type of data
WEB_SOCKET_INVALID_PAYLOAD_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1007;
Data within a message is not consistent with the type of the message
WEB_SOCKET_MAX_CLOSE_REASON_LENGTH = 123;
Https://msdn.microsoft.com/en-us/library/windows/desktop/hh449347
WEB_SOCKET_MESSAGE_TOO_BIG_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1009;
The message sent was too large to process
WEB_SOCKET_PING_PONG_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000005;
The buffer contains a ping or pong message
- when sending, this value means 'ping'
- when processing received data, this value means 'pong'
WEB_SOCKET_POLICY_VIOLATION_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1008;
The message violates an endpoint's policy
WEB_SOCKET_PROTOCOL_ERROR_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1002;
Peer detected protocol error and it is closing the connection
WEB_SOCKET_SECURE_HANDSHAKE_ERROR_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1015;
The TLS handshake could not be completed
WEB_SOCKET_SERVER_ERROR_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1011;
An unexpected condition prevented the server from fulfilling the request
WEB_SOCKET_SUCCESS_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1000;
Close completed successfully
WEB_SOCKET_UNSOLICITED_PONG_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000006;
The buffer contains an unsolicited pong message
WEB_SOCKET_UNSUPPORTED_EXTENSIONS_CLOSE_STATUS: WEB_SOCKET_CLOSE_STATUS = 1010;
A client endpoint expected the server to negotiate one or more extensions, but the server didn't return them in the response message of the WebSocket handshake
WEB_SOCKET_URL_CONTEXT = 1;
Context ID of WebSocket URI group
WEB_SOCKET_UTF8_FRAGMENT_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000001;
The buffer contains part of a UTF-8 message
WEB_SOCKET_UTF8_MESSAGE_BUFFER_TYPE: WEB_SOCKET_BUFFER_TYPE = $80000000;
The buffer contains the last, and possibly only, part of a UTF-8 message
WINHTTP_CALLBACK_STATUS_RESOLVING_NAME = $00000001;
WINHTTP_DISABLE_COOKIES = $00000001;
Values for WINHTTP_OPTION_DISABLE_FEATURE
WINHTTP_ENABLE_SSL_REVOCATION = $00000001;
Values for WINHTTP_OPTION_ENABLE_FEATURE
WINHTTP_FLAG_SECURE_PROTOCOL_SSL2 = $00000008;
Values for WINHTTP_OPTION_SECURE_PROTOCOLS
WINHTTP_INVALID_STATUS_CALLBACK = -1;
If the following value is returned by WinHttpSetStatusCallback, then probably an invalid (non-code) address was supplied for the callback
WINHTTP_NO_CLIENT_CERT_CONTEXT = $00000000;
Value for WINHTTP_OPTION_CLIENT_CERT_CONTEXT
WINHTTP_OPTION_REDIRECT_POLICY_NEVER = 0;
Windows 11 or Windows Server 2022 ;) values for WINHTTP_OPTION_REDIRECT_POLICY
WINHTTP_OPTION_SECURITY_FLAGS = 31;
See https://learn.microsoft.com/en-us/windows/win32/winhttp/option-flags
Functions or procedures | Description | |
---|---|---|
HttpApiInitialize | Ensure that the http.sys API has been loaded | |
HttpSys2ToWebSocketHeaders | Retrieve an array of headers from WebSockets low-level information | |
RegURL | Compute a http.sys compatible URI from https://root:port fields | |
RetrieveHeadersAndGetRemoteIPConnectionID | Low-level adjustement of the HTTP_REQUEST headers | |
SysErrorMessageWinInet | Retrieve extended error information text after a WinINet API call | |
WebSocketApiInitialize | Low-level loading of the WebSockets API | |
WebSocketHeadersToText | Retrieve the linefeed separated text from WebSockets array of headers | |
WinHttpApiInitialize | Low-level thread-safe initialization of the WinHtpp API | |
WinHttpGetProxyInfo | Use WinHttp to retrieve the proxy information needed to access a given URI | |
WinHttpSecurityErrorCallback | A callback raising a EWinHttp on error | |
WinHttp_WebSocketEnabled | Is HTTP.SYS web socket API available on the target system Windows 8 and UP |
procedure HttpApiInitialize;
Ensure that the http.sys API has been loaded
function HttpSys2ToWebSocketHeaders( const aHttpHeaders: HTTP_REQUEST_HEADERS): WEB_SOCKET_HTTP_HEADER_ARR;
Retrieve an array of headers from WebSockets low-level information
function RegURL(aRoot, aPort: RawUtf8; Https: boolean; aDomainName: RawUtf8): SynUnicode;
Compute a http.sys compatible URI from https://root:port fields
function RetrieveHeadersAndGetRemoteIPConnectionID(const Request: HTTP_REQUEST; const RemoteIPHeadUp, ConnectionIDHeadUp: RawUtf8; out RemoteIP: RawUtf8; var ConnectionID: QWord): RawUtf8;
Low-level adjustement of the HTTP_REQUEST
headers
function SysErrorMessageWinInet(error: integer): RawUtf8;
Retrieve extended error information text
after a WinINet API call
procedure WebSocketApiInitialize;
Low-level loading of the WebSockets API
function WebSocketHeadersToText(const aHeaders: PWEB_SOCKET_HTTP_HEADER; const aHeadersCount: integer): RawUtf8;
Retrieve the linefeed separated text
from WebSockets array of headers
procedure WinHttpApiInitialize(RaiseOnError: boolean = true);
Low-level thread-safe initialization of the WinHtpp API
function WinHttpGetProxyInfo(const URL: SynUnicode; out ProxyInfo: TProxyInfo): DWORD;
Use WinHttp to retrieve the proxy information needed to access a given URI
- it will first try to return the Internet Explorer settings, then try to create a WinHttp client connection, and retrieve the proxy information
- will parse any system-defined Proxy Auto-Configuration (PAC) file if needed
- returns 0 on success, or an error code on failure - see also ErrorMessage - e.g. ERROR_WINHTTP_AUTODETECTION_FAILED
(12180)
- note that this call may require a network access, and can be slow: if you can, try to store
the proxy information in the settings, and only call it in case of connection failure
- as called by cross-platform GetProxyForUri
() function from mormot.net.client
procedure WinHttpSecurityErrorCallback(hInternet: hInternet; dwContext: PDWORD; dwInternetStatus: cardinal; lpvStatusInformation: pointer; dwStatusInformationLength: cardinal); stdcall;
A callback raising a EWinHttp
on error
function WinHttp_WebSocketEnabled: boolean;
Is HTTP.SYS web socket API available on the target system Windows 8 and UP