我需要将http post请求中的大量数据发送到支持gziped编码请求的服务器。
从简单的
开始public async Task<string> DoPost(HttpContent content)
{
HttpClient client = new HttpClient();
HttpResponseMessage response = await client.PostAsync("http://myUri", content);
response.EnsureSuccessStatusCode();
return await response.Content.ReadAsStringAsync();
}
我刚刚添加了预压缩
public async Task<string> DoPost(HttpContent content, bool compress)
{
if (compress)
content= await CompressAsync(content);
return await DoPost(content);
}
private static async Task<StreamContent> CompressAsync(HttpContent content)
{
MemoryStream ms = new MemoryStream();
using (GZipStream gzipStream = new GZipStream(ms, CompressionMode.Compress, true))
{
await content.CopyToAsync(gzipStream);
await gzipStream.FlushAsync();
}
ms.Position = 0;
StreamContent compressedStreamContent = new StreamContent(ms);
compressedStreamContent.Headers.ContentType = content.Headers.ContentType;
compressedStreamContent.Headers.Add("Content-Encoding", "gzip");
return compressedStreamContent;
}
它工作正常但压缩数据在发送请求之前完全加载到内存中。我希望能够在以流媒体方式发送时动态压缩数据。
为此,我尝试了以下代码:
private static async Task<HttpContent> CompressAsync2(HttpContent content)
{
PushStreamContent pushStreamContent = new PushStreamContent(async (stream, content2, transport) =>
{
using (GZipStream gzipStream = new GZipStream(stream, CompressionMode.Compress, true))
{
try
{
await content.CopyToAsync(gzipStream);
await gzipStream.FlushAsync();
}
catch (Exception exception)
{
throw;
}
}
});
pushStreamContent.Headers.ContentType = content.Headers.ContentType;
pushStreamContent.Headers.Add("Content-Encoding", "gzip");
return pushStreamContent;
}
但它永远不会离开CopyToAsync(gzipStream)。 FlushAsync永远不会被执行,也不会抛出任何异常,Fiddler也看不到任何帖子。
我的问题是:
非常感谢任何帮助。
答案 0 :(得分:13)
尝试使用WebAPIContrib https://github.com/WebApiContrib/WebAPIContrib/blob/master/src/WebApiContrib/Content/CompressedContent.cs
中的CompressedContent类public async Task<string> DoPost(HttpContent content)
{
HttpClient client = new HttpClient();
HttpResponseMessage response = await client.PostAsync("http://myUri",
new CompressedContent(content,"gzip"));
response.EnsureSuccessStatusCode();
return await response.Content.ReadAsStringAsync();
}
P.S。这只会流式传输.net 4.5上的内容。 .net 4版本的HttpWebRequest始终缓冲已发送的内容。
P.P.S。为每个请求创建一个新的HttpClient不是使用HttpClient的最佳方式。执行此操作将强制为每个请求创建新的TCP连接。