加载中...

a标签下载附件,无法下载、无法重命名?怎么回事


一、 为什么a标签无法下载,无法重命名?

这就与 a 标签的 href 有很大的关系, href 属性的地址必须是 同源 URL,否则,download 就会不起作用。

  1. 同源 URL 会进行 下载 操作
  2. 非同源 URL 会进行 导航 操作
  3. 非同源的资源 仍需要进行下载,那么可以将其转换为 blob: URL 形式

二、a 标签属性介绍

<a>download 属性是HTML5新增的属性,它可以使 a 标签的 href 属性进行下载,download 属性为下载后的 文件名,但是:

  1. 这个值可能会通过 JavaScript 进行动态修改
  2. 或者 Content-Disposition 中指定的 download 属性优先级高于 a.download

三、下载方法

注意:以下3种方式,是对文件的 链接地址 所写的方案(例:http://127.0.0.1:3000/1.jpg)

*[HTML]: 超文本标记语言

1、同源URL
  1. 静态方式
<a href="http://127.0.0.1:3000/1.jpg" download="1.jpg">下载</a>
  1. 动态方式
function aTagDownload(url, filename){
  const a = document.createElement("a"); // 创建 a 标签
  a.href = url; // 下载路径
  a.download = filename;  // 下载属性,文件名
  a.style.display = "none"; // 不可见
  document.body.appendChild(a); // 挂载
  a.click(); // 触发点击事件
  document.body.removeChild(a); // 移除
} 
2、非同源URL
  1. Blob 方式
function download(path, fileName=''){
  if (!fileName) fileName = '123.jpg'
  fetch(path).then(res => 
    res.blob()
  ).then((blob) => {
    let objectUrl = URL.createObjectURL(blob); // 创建 url 对象
    aTagDownload(objectUrl,fileName); // 调用 上面 [2] 动态方式
  }).catch((err) => {
    console.log('Request Failed', err)
  })
}

四、接口返回文件流(例:Excel、word、PDF文件)

// excelExport后台接口
// 请求接口时需要增加 responseType: `blob`,不然下载的文件内容会乱码
excelExport(params).then(res => {
	if (!res) return;
    excelDownload(res) // 调用下载方法  res 二进制流
});

function excelDownload(res){
  let fileReader = new FileReader();
  fileReader.onload = function() {//对于blob文件流进行转换,拿到接口返回的状态码以及提示语
    try {
      let jsonData = JSON.parse(this.result)
      if(jsonData.status == 403){ // 403:禁止访问
        logOut(jsonData.reason); // logOut 退出登录
        return;
      }
      } catch (err) {
    }
  };
  fileReader.readAsText(res)
  // 这个window.fileName我是在接口响应处获取的
  // window.fileName = response.headers['content-disposition'] && response.headers['content-disposition'].split(`filename=`)[1];
  const fileName = window.decodeURI(window.fileName);
  
  const suffix = fileName.split('.')[1];  // 文件类型
  let blob = new Blob([res], { type: FileType[suffix] }); // 创建 blob 对象
  let objectUrl = URL.createObjectURL(blob); // 创建 url 对象
  aTagDownload(objectUrl,fileName) // 调用 上面 [2] 动态方式
}

文章作者: LYF
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 LYF !
评论
  目录