fetch获取下载进度

132 阅读1分钟
// 下载cos上的资源
import { ElMessage } from 'element-plus'
import { unLoading } from '@/utils/unLoading'
import { ref } from 'vue'
export async function download(url, fileName) {
  const rate = ref(0)
  const loading = unLoading(rate)
  const blob = await fetch(url).then(async (res) => {
    // 1. 获取reader
    const reader = res.body.getReader()
    // 2. 获得总长度(length)
    const contentLength = +res.headers.get('Content-Length');

    // 3. 读取数据
    let receivedLength = 0; // 当前接收到了这么多字节
    let chunks = []; // 接收到的二进制块的数组(包括 body)

    while(true) {
      const {done, value} = await reader.read();

      if (done) {
        break;
      }

      chunks.push(value);
      receivedLength += value.length;
      rate.value = Math.floor(receivedLength/contentLength * 100) + '%'
    }

    return new Blob(chunks, {type: 'application/octet-stream'}); // 把二进制块组合成一个文件
  });
  loading.close()
  ElMessage.success('下载成功')
  const blobUrl = window.URL.createObjectURL(blob);
  const link = document.createElement("a");
  link.style.display = "none";
  link.target = "_blank";
  link.href = blobUrl;
  // 从url获取文件扩展名
  const ext = url.split('.').pop();
  link.download = `${fileName}.${ext}`;
  document.body.appendChild(link);
  link.click();
}