• 前端下载文件的几种方式


    1、使用 location.href 

    // 适用于浏览器无法识别文件,如果是html、jpg、pdf等会直接解析展示,而不会下载

    window.location.href = url

    2、使用 window.open

    // 适用于浏览器无法识别文件,如果是html、jpg、pdf等会直接解析展示,而不会下载

    window.open(url)

    3、a 标签

    // 适用于单文件下载或需要自定义文件名称
    
    //写法1
    const download = (filename, url) => {
        let a = document.createElement('a'); 
        a.style = 'display: none'; // 创建一个隐藏的a标签
        a.download = filename;
        a.href = url;
        document.body.appendChild(a);
        a.click(); // 触发a标签的click事件
        document.body.removeChild(a);
    }
    // 写法2
    < a href="/images/download.jpg" download="myFileName">
    
    4、文件流

    step1 发送请求,有两种方式
    // 此种方式的优点是支持多文件下载、post下载、自定义文件名称,流程是向后端发送post请求,后端返回文件流,前端将文件流转成下载链接
    
    // 原生js请求写法(不可以使用JQuery,因为JQuery不支持blob类型)
    function download() {
         const req = new XMLHttpRequest();
        req.open('POST', '/download/excel', true);
        req.responseType = 'blob'; //如果不指定,下载后文件会打不开
        req.setRequestHeader('Content-Type', 'application/json');
        req.onload = function() {
          var content = req.getResponseHeader("Content-Disposition") ;
          // 文件名最好用后端返的Content-disposition
          // 需要后端设置 Access-Control-Expose-Headers: Content-disposition 使得浏览器将该字段暴露给前端
          var name = content && content.split(';')[1].split('filename=')[1];
          var fileName = decodeURIComponent(name)
          downloadFile(req.response,fileName)  // 调用将文件流转成文件的方法,后面有写
        };
        req.send( JSON.stringify(params));
    
    }
    
    // axios请求写法
    function download() {
      axios({
        method: 'post',
        headers: {
          'Content-Type': 'application/json; charset=utf-8'
        },
        url: '/robot/strategyManagement/analysisExcel',
        responseType: 'blob',
        headers: { //如果需要权限下载的话,加在这里
          Authorization: '123456'
        }
        data: JSON.stringify(params),
      }).then(function(res){
        var content = res.headers['content-disposition'];
        var name = content && content.split(';')[1].split('filename=')[1];
        var fileName = decodeURIComponent(name)
        downloadFile(res.data,fileName)// 调用将文件流转成文件的方法,后面有写
      }) 
    }

    step2 处理文件流下载

      方式一: 通过URL.createObjectURL()下载

    // URL.createObjectURL() 静态方法会创建一个DOMString,其中包含一个表示参数中给出的对象的URL。这个 URL 的生命周期和创建它的窗口中的document绑定
    
    downloadFile:function(data,fileName){
        // data为blob格式
        var blob = new Blob([data]);
        var downloadElement = document.createElement('a');
        var href = window.URL.createObjectURL(blob);
        downloadElement.href = href;
        downloadElement.download = fileName;
        document.body.appendChild(downloadElement);
        downloadElement.click();
        document.body.removeChild(downloadElement);
        window.URL.revokeObjectURL(href);
    }

      方式二:通过# FileReader.readAsDataURL()下载

    // readAsDataURL() 方法会读取指定的 Blob 或 File 对象。读取操作为异步操作,当读取完成时,可以从onload回调函数中通过实例对象的result属性获取data:URL格式的字符串(base64编码),此字符串即为读取文件的内容,可以放入a标签的href属性中
    downloadFile:function(data,fileName){
       const reader = new FileReader()
       // 传入被读取的blob对象
       reader.readAsDataURL(data)
       // 读取完成的回调事件
       reader.onload = (e) => {
           let a = document.createElement('a')
           a.download = fileName
           a.style.display = 'none'
           // 生成的base64编码
           let url = reader.result
           a.href = url
           document.body.appendChild(a)
           a.click()
           document.body.removeChild(a)
       }
    }

     readAsDataURL 和 createObjectURL 对比

      readAsDataURL (blob) createObjectURL (blob)
    返回值 可以得到一段base64的字符串 得到的是当前文件的一个内存url
    内存 js垃圾回收机制自动从内存中清理 存在于当前document内,清除方式通过revokeObjectURL()手动清除
    执行方式 通过回调的方式f返回,异步执行 直接返回,同步执行
    多个文件 同时处理多个文件时,需要一个文件对应一个FileReader对象 依次返回,没有影响
    优势对比 可直接转为base64格式,直接用于业务 得到本地内存容器的URL地址,方便预览,需要注意手动释放内存的问题,性能优秀
    只要你不觉得尴尬,那尴尬的就是别人
  • 相关阅读:
    个人理解闭包
    个人理解回调
    在网站中设置一个分享到功能
    在lua中从一个字符串中移除空间源码
    成都实行积分落户
    unity3D客户端框架
    skynet对Windows环境支持的版本:Windows版skynet
    超期羁押
    资料
    媒体电话
  • 原文地址:https://www.cnblogs.com/wujiaxing/p/15090200.html
Copyright © 2020-2023  润新知