前言
最近有个需求,涉及到文件下载相关内容,项目基本开发完成,做了个总结
使用window.open或者window.href = xxx
// 仅支持 不可以直接打开的文件类型,如果可以直接查看的文件类型,打开的话会直接显示
// window.open('https://aa.pdf')
window.open('https://aa.zip')
// 仅支持 不可以直接打开的文件类型,如果可以直接查看的文件类型,打开的话会直接在当前页显示
// window.location.href = 'https://bb.pdf'
window.location.href = 'https://bb.zip'
注意点:
1.会出现URL长度限制问题
2.需要注意url编码问题
使用 a href download
<h3>非跨域文件:</h3>
<a href="@/assets/img/IMG_1949.pdf" download="11.pdf">pdf </a>
<a href="@/assets/img/IMG_1949.zip" download="11.zip">zip </a>
<a href="@/assets/img/IMG_1949.jpeg" download="11.jpeg">png </a>
<h3>跨域文件:可以直接打开的文件是无法下载的,无法直接打开的文件可以下载,但是无法修改文件名</h3>
<a href="https://cc.pdf" download>pdf </a>
<a href="https:/cc.zip" download="11.zip">zip </a>
<a href="cc" download>png </a>
注意点:
1.非跨域文件在chrome下是没问题的,跨域文件只有直接打不开的文件才可以下载(zip,rar等)
2.跨域文件即使能下载,也不能使用download属性修改下载下来的文件名
利用二进制文件下载
进行下载的思路很简单:发请求获取二进制数据,转化为Blob对象,利用URL.createObjectUrl生成url地址,赋值在a标签的href属性上,结合download进行下载。
/**
* 下载文件
* @param {String} path - 下载地址/下载请求地址。
* @param {String} name - 下载文件的名字/重命名(考虑到兼容性问题,最好加上后缀名)
*/
downloadFile (path, name) {
const xhr = new XMLHttpRequest();
xhr.open('get', path);
xhr.responseType = 'blob';
xhr.send();
xhr.onload = function () {
if (this.status === 200 || this.status === 304) {
// 如果是IE10及以上,不支持download属性,采用msSaveOrOpenBlob方法,但是IE10以下也不支持msSaveOrOpenBlob
if ('msSaveOrOpenBlob' in navigator) {
navigator.msSaveOrOpenBlob(this.response, name);
return;
}
// const blob = new Blob([this.response], { type: xhr.getResponseHeader('Content-Type') });
// const url = URL.createObjectURL(blob);
const url = URL.createObjectURL(this.response);
const a = document.createElement('a');
a.style.display = 'none';
a.href = url;
a.download = name;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
URL.revokeObjectURL(url);
}
};
}
注意:
1.可以指定文件名
2.下载文件的进度需要自己实现,而且用户的体验没有直接下载好
3.这种情况更适用于知道了文件的所有信息,文件名,类型等,直接下载文件改名
非公共方案
对于七牛云平台,参考链接:developer.qiniu.com/kodo/1659/d…
<a :href="http://baidu.com/a.pdf?attname=a.pdf}`">下载</a>