.net HttpClient 如何实现下载文件获取进度
一般客户端上传或者下载文件都需要一个进度来给用户反馈,如果用的以前的webclient webrequest的话那就网上有很多的资料来看怎么实现,但是目前用的比较多的还是httpclient 但是用这个之后就不知道怎么去获取下载文件的进度了。 所以这次记一下自己的实现办法。(用的办法也不是很好,需要实现知道文件的总大小。所以我是先一个get请求获取文件的大小然后 再去请求文件流。)
先上一段代码
Stream stream = httpClient.GetStreamAsync(RequestUrl).Result;
Task check = null;
using (FileStream filestream = File.Open(DownLoadSavePath, FileMode.Create))
{
Task task = stream.CopyToAsync(filestream);
check = new Task(()=> {
while (!task.IsCompleted)
{
float value = (float)filestream.Length / (float)filesize;
//if(value > 1)
//{
// value = 1;
//}
action?.Invoke(value, "下载进度 : ");
Thread.Sleep(1000);
}
return;
});
check.Start();
task.Wait();
}
stream.Close();
stream.Dispose();
stream = null;
check.Wait();
///设置更新完成
action?.Invoke(1, "下载进度 : ");
现在就是假如我们已经获取了需要下载的文件的总大小了,然后Stream stream = httpClient.GetStreamAsync(RequestUrl).Result;来获取文件的下载流,然后通过Task task = stream.CopyToAsync(filestream); 将流里面的信息异步拷贝到文件流,这里的信息不是一次性拷贝完成的是实际上是一点一点完成的所以在开始拷贝的时候开启一个任务去读取已经拷贝了多少个字节
check = new Task(()=> {
while (!task.IsCompleted)
{
float value = (float)filestream.Length / (float)filesize;
//if(value > 1)
//{
// value = 1;
//}
action?.Invoke(value, "下载进度 : ");
Thread.Sleep(1000);
}
return;
});
这一段代码就是相当于开了另外一个线程去读取 已经从服务器上下载了多少个字节了然后除以总的文件大小(字节数)就是当前的进度了。方法比较另类,希望有更好的办法的朋友留言指教一下。提前感谢!
还有服务器上的代码。服务器是用.net core写的代码奉上:
string rootdir = VersionUpdateService.GetLastUpdateConfig();
if(rootdir != null)
{
string file = Directory.GetFiles(rootdir, "*.zip", SearchOption.TopDirectoryOnly).First();
using (FileStream stream = System.IO.File.OpenRead(file))
{
byte[] datas = new byte[stream.Length];
stream.Read(datas, 0, datas.Length);
object statu = new object();
var req = HttpContext.Response.Body.BeginWrite(datas, 0, datas.Length, _ => { }, statu);
HttpContext.Response.Body.EndWrite(req);
datas = null;
statu = null;
}
HttpContext.Response.Body.Flush();
//HttpContext.Response.Body.EndWrite();
returnObj.SetIsSuccess(true);
}