共计 2072 个字符,预计需要花费 6 分钟才能阅读完成。
问题形容
- 应用 axios 发申请,想要实现一个申请的后果进度
- 比方当网络慢的状况,或者某个申请返回的数据量比拟大的状况等
- 最常见的就是下载一个大文件,要查看大文件下载的进度
- axios 的 onDownloadProgress 函数曾经帮咱们封装好了
- 是基于原生的 ProgressEvent 套壳子的
比方咱们下载一个流文件,要出现下载的进度,在这里打印一下进度事件
axios({
method: "get",
responseType: "blob", // 流文件为 blob 类型
url: "http://ashuai.work:10000/getDoc",
onDownloadProgress(ProgressEvent) {console.log('进度事件', ProgressEvent);
}
}).then(({data}) => {console.log('接口申请实现',data);
});
打印后果如下图:
这里为何拿不到 total 的值?
- 是因为接口的响应头,没有返回 Content-Length 属性
- 所以 ProgressEvent 就拿不到这个值,所以就没有 total 的值,就为 undefined
请看响应头
Content-Length 大家能够简要了解成为一个接口返回的内容的总大小,单位字节,咱们晓得了某个时刻 loaded 多少字节,晓得总字节,就能够得出百分比了
解决方案
让后端在响应头上加上 Content-Length 即可
让后端在响应头上加上 Content-Length 即可
让后端在响应头上加上 Content-Length 即可
笔者这里应用 express 演示一下代码:
route.get('/getDoc', (req, res) => {res.header('Access-Control-Allow-Origin', '*');
// fs.statSync 读取文件信息,读取当前目录下的 study.docx 文件
let docxUrl = './doc/study.docx'
const Myfilesize = fs.statSync(docxUrl).size // 拿到文件字节大小
// 设置申请头
res.writeHead(200, {
'Content-Type': 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
'content-length': Myfilesize // 加上即可
})
let readStream = fs.createReadStream(docxUrl) // 流文件 pipe 管道返回
readStream.pipe(res);
})
加上当前,响应头就有 Content-Length 了,就能失常了
这样的话,进度条成果也就有了
流文件申请手动加上,一般的申请会自带 Content-Length 的
代码附上
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<script src="https://cdn.bootcdn.net/ajax/libs/axios/1.3.5/axios.js"></script>
<title> 申请接口进度 </title>
</head>
<body>
<button @click="goPreview"> 点击预览 word 文件 </button>
<br>
<progress max="100" value="0"></progress> <span class="val">0</span>
<script>
let btn = document.querySelector('button')
let prog = document.querySelector('progress')
let v = document.querySelector('.val')
btn.onclick = () => {
axios({
method: "get",
responseType: "blob", // 流文件为 blob 类型
url: "http://ashuai.work:10000/getDoc",
onDownloadProgress(ProgressEvent) {let percent = Math.floor((ProgressEvent.loaded / ProgressEvent.total) * 100)
prog.setAttribute('value', percent)
v.innerHTML = percent + '%'
console.log('进度事件', ProgressEvent);
}
}).then(({data}) => {console.log(data); // 后端返回的是流文件
});
}
</script>
</body>
</html>
正文完