IHttpResponse::WriteEntityChunks 方法
将一个或多个 HTTP_DATA_CHUNK 结构追加到响应正文。
语法
virtual HRESULT WriteEntityChunks(
IN HTTP_DATA_CHUNK* pDataChunks,
IN DWORD nChunks,
IN BOOL fAsync,
IN BOOL fMoreData,
OUT DWORD* pcbSent,
OUT BOOL* pfCompletionExpected = NULL
) = 0;
parameters
pDataChunks
[IN]指向一个或多个 HTTP_DATA_CHUNK
结构的指针。
nChunks
[IN]一个 , DWORD
它包含 指向 pDataChunks
的区块数。
fAsync
[IN] true
如果方法应异步完成,则为 ;否则为 false
。
fMoreData
[IN] true
如果要在响应中发送更多数据,则为 ; false
如果这是最后一个数据,则为 。
pcbSent
[OUT]如果调用同步完成,则发送到客户端的字节数。
pfCompletionExpected
[OUT] true
如果此调用的异步完成挂起,则为 ;否则为 false
。
返回值
HRESULT
。 可能的值包括(但并不限于)下表中的项。
值 | 说明 |
---|---|
S_OK | 指示操作成功。 |
ERROR_INVALID_PARAMETER | 指示参数无效 (例如, pDataChunks 指针设置为 NULL) 。 |
ERROR_NOT_ENOUGH_MEMORY | 指示内存不足,无法执行操作。 |
ERROR_ARITHMETIC_OVERFLOW | 已向响应添加超过 65535 个区块。 |
备注
开发人员可以使用 WriteEntityChunks
方法将单个 HTTP_DATA_CHUNK
结构或结构数组 HTTP_DATA_CHUNK
插入响应正文中。 如果操作已同步完成,则 pcbSent
参数将接收已插入响应的字节数。
如果打开缓冲,该方法 WriteEntityChunks
将创建任何 HTTP_DATA_CHUNK
结构的副本,从而复制基础数据,以便无需保留它。 如果缓冲已关闭,或达到响应缓冲区限制,则 WriteEntityChunks
方法还将刷新响应。 如果缓冲关闭且 fAsync
参数为 true
,则必须保留内存,直到请求完成。
通过将 参数true
设置为 fAsync
,可以将操作配置为WriteEntityChunks
异步完成。 在这种情况下, WriteEntityChunks
方法将立即返回给调用方,并且 pcbSent
参数不会接收插入到响应中的字节数。 如果禁用缓冲并且 fAsync
参数为 true
,则必须保留参数的 pDataChunks
内存,直到异步调用完成。
最多可以向请求写入 65535 个区块, (64 KB 减去 1) 。
示例
以下示例演示如何使用 WriteEntityChunks
方法创建 HTTP 模块,该模块将包含两个数据区块的数组插入响应中。 然后,该示例将响应返回到 Web 客户端。
#define _WINSOCKAPI_
#include <windows.h>
#include <sal.h>
#include <httpserv.h>
// Create the module class.
class MyHttpModule : public CHttpModule
{
public:
REQUEST_NOTIFICATION_STATUS
OnBeginRequest(
IN IHttpContext * pHttpContext,
IN IHttpEventProvider * pProvider
)
{
UNREFERENCED_PARAMETER( pProvider );
// Create an HRESULT to receive return values from methods.
HRESULT hr;
// Create an array of data chunks.
HTTP_DATA_CHUNK dataChunk[2];
// Buffer for bytes written of data chunk.
DWORD cbSent;
// Create string buffers.
PCSTR pszOne = "First chunk data\n";
PCSTR pszTwo = "Second chunk data\n";
// Retrieve a pointer to the response.
IHttpResponse * pHttpResponse = pHttpContext->GetResponse();
// Test for an error.
if (pHttpResponse != NULL)
{
// Clear the existing response.
pHttpResponse->Clear();
// Set the MIME type to plain text.
pHttpResponse->SetHeader(
HttpHeaderContentType,"text/plain",
(USHORT)strlen("text/plain"),TRUE);
// Set the chunk to a chunk in memory.
dataChunk[0].DataChunkType = HttpDataChunkFromMemory;
// Set the chunk to the first buffer.
dataChunk[0].FromMemory.pBuffer =
(PVOID) pszOne;
// Set the chunk size to the first buffer size.
dataChunk[0].FromMemory.BufferLength =
(USHORT) strlen(pszOne);
// Set the chunk to a chunk in memory.
dataChunk[1].DataChunkType = HttpDataChunkFromMemory;
// Set the chunk to the second buffer.
dataChunk[1].FromMemory.pBuffer =
(PVOID) pszTwo;
// Set the chunk size to the second buffer size.
dataChunk[1].FromMemory.BufferLength =
(USHORT) strlen(pszTwo);
// Insert the data chunks into the response.
hr = pHttpResponse->WriteEntityChunks(
dataChunk,2,FALSE,TRUE,&cbSent);
// Test for an error.
if (FAILED(hr))
{
// Set the error status.
pProvider->SetErrorStatus( hr );
}
// End additional processing.
return RQ_NOTIFICATION_FINISH_REQUEST;
}
// Return processing to the pipeline.
return RQ_NOTIFICATION_CONTINUE;
}
};
// Create the module's class factory.
class MyHttpModuleFactory : public IHttpModuleFactory
{
public:
HRESULT
GetHttpModule(
OUT CHttpModule ** ppModule,
IN IModuleAllocator * pAllocator
)
{
UNREFERENCED_PARAMETER( pAllocator );
// Create a new instance.
MyHttpModule * pModule = new MyHttpModule;
// Test for an error.
if (!pModule)
{
// Return an error if the factory cannot create the instance.
return HRESULT_FROM_WIN32( ERROR_NOT_ENOUGH_MEMORY );
}
else
{
// Return a pointer to the module.
*ppModule = pModule;
pModule = NULL;
// Return a success status.
return S_OK;
}
}
void Terminate()
{
// Remove the class from memory.
delete this;
}
};
// Create the module's exported registration function.
HRESULT
__stdcall
RegisterModule(
DWORD dwServerVersion,
IHttpModuleRegistrationInfo * pModuleInfo,
IHttpServer * pGlobalInfo
)
{
UNREFERENCED_PARAMETER( dwServerVersion );
UNREFERENCED_PARAMETER( pGlobalInfo );
// Set the request notifications and exit.
return pModuleInfo->SetRequestNotifications(
new MyHttpModuleFactory,
RQ_BEGIN_REQUEST,
0
);
}
模块必须导出 RegisterModule 函数。 可以通过为项目创建模块定义 (.def) 文件导出此函数,也可以使用 开关编译模块 /EXPORT:RegisterModule
。 有关详细信息,请参阅 演练:使用本机代码创建Request-Level HTTP 模块。
可以选择使用调用约定编译代码, __stdcall (/Gz)
而不是为每个函数显式声明调用约定。
要求
类型 | 说明 |
---|---|
客户端 | - Windows Vista 上的 IIS 7.0 - Windows 7 上的 IIS 7.5 - Windows 8 上的 IIS 8.0 - Windows 10 上的 IIS 10.0 |
服务器 | - Windows Server 2008 上的 IIS 7.0 - Windows Server 2008 R2 上的 IIS 7.5 - Windows Server 2012 上的 IIS 8.0 - Windows Server 2012 R2 上的 IIS 8.5 - Windows Server 2016 上的 IIS 10.0 |
产品 | - IIS 7.0、IIS 7.5、IIS 8.0、IIS 8.5、IIS 10.0 - IIS Express 7.5、IIS Express 8.0、IIS Express 10.0 |
Header | Httpserv.h |
另请参阅
IHttpResponse 接口
IHttpResponse::WriteEntityChunkByReference 方法