我有一个WinRT应用程序(8.0,而不是8.1,所以我不能使用Windows.Web.HttpClient)我将大文件上传到站点。我正在使用System.Net.Http.HttpClient和Microsoft.AspNet.WebApi.Client nuget包中的System.Net.Http.Handlers.ProgressMessageHandler来跟踪进度。
无论我上传的文件有多大,我似乎总是只调用一次HttpSendProgress事件,只进行一次,进度为100%(和totalBytes == sentBytes)。然而,该文件实际上并没有完成上传到网站,直到事件发生后的某个时间,具体取决于文件大小以及我是否限制了上传速度等。上传确实有效,但进度报告是无用的。
我使用了一个网络监控工具,可以看到调用进度事件后缓慢传输的数据(当我在断点停止后让应用程序运行时) - 但是我只将事件提升了一次并且有100次上传完成前的进度百分比。
我认为HttpClient写入某种缓冲区的速度比实际上传速度快得多,但我无法弄清楚如何更改/阻止它,或者ProgressMessageHandler类的重点是什么呢?总是以这种方式工作。
目前我使用的代码看起来像下面这样;
public static async Task<string> UploadDataAsync(string uploadUrl, byte[] data, string contentTypeHeader, string oauthHeader, Action<long, long?> progressCallback)
{
var ph = new System.Net.Http.Handlers.ProgressMessageHandler();
if (progressCallback != null)
{
ph.HttpSendProgress += (sender, args) =>
{
progressCallback(args.BytesTransferred, args.TotalBytes);
};
}
var client = HttpClientFactory.Create(ph);
client.Timeout = new TimeSpan(0, 20, 0);
if (!String.IsNullOrEmpty(oauthHeader))
client.DefaultRequestHeaders.Add("Authorization", oauthHeader);
var content = new ByteArrayContent(data);
content.Headers.TryAddWithoutValidation("Content-Type", contentTypeHeader);
var postResponse = await client.PostAsync(new Uri(uploadUrl), content);
var result = await postResponse.Content.ReadAsStringAsync();
if (!postResponse.IsSuccessStatusCode)
{
throw new OAuthException(result);
}
return result;
}
答案 0 :(得分:0)
我建议您使用ContinueWith
将这两项任务联系起来,并使用TaskContinuationOptions.OnlyOnRanToCompletion
让ProgressMessageHandler
有机会完全按照您的意愿报告进度。
希望这可能会有所帮助。
postResponse.ContinueWith(task =>
{
if (task.Result.IsSuccessStatusCode)
{
}
}, TaskContinuationOptions.OnlyOnRanToCompletion);