主题
前端文件下载方案
1. 后端返回文件url路径的场景
该方式将下载逻辑放在后端处理,后端直接返回文件url地址
js
window.location.herf = 'xxxxx' // xxxxx为后端返回的文件路径
2. 后端返回二进制流的场景
根据二进制流数据生成下载URL可以有多种方式实现,具体实现如下:
方案1. 将二进制数据封装为BLOB对象
前端通过创建a标签,为href属性赋值,模拟自动点击事件,最后在清除a标签即可,使用到URL.createObjectURL(object)这个方法.
接收后端传过来的二进制流。默认情况下axios不会处理二进制数据,即请求可以正常被浏览器接收,但是axios不会去处理。需要在请求的时候设置responseType: 'blob'才可以
js
// get 请求
axios({
method: 'get',
url, // 这里自行设置传参
params, // 这里自行设置传参
responseType:'blob' // 这里是重点,敲黑板
}).then(res => {
// 获取响应头中的文件名
let filename = response.headers //下载后文件名
filename = filename["content-disposition"]
filename = filename.split(";")[1].split("filename=")[1]
// 创建 a 标签
let elink = document.createElement('a');
document.body.appendChild(elink);
elink.style.display = 'none'; // 隐藏起来
elink.download = filename
// 如果后端没有返回,可以自己设置下载文件的名称 elink.download = 'XXX文件.pdf';
let blob = new Blob([res.data]);
// 兼容webkix浏览器,处理webkit浏览器中herf自动添加blob前缀,默认在浏览器打开而不是下载
const URL = window.URL || window.webkitURL
elink.href = URL.createObjectURL(blob) // 通过createObjectURL方法转换成对象url
elink.click();
document.body.removeChild(elink);
URL.revokeObjectURL(elink.href); // 释放URL 对象
})
方案2. 将二进制数据封装为文件读取FileReader对象
注意: 使用 FileReader对象封装二进制流之后没办法设置下载的文件名,默认文件名为下载,文件格式根据读取的是请求返回的content-type。
js
// utils.js
export const download = (res) => {
// 创建文件对象
let reader = new FileReader()
// 监听读取完毕
reader.onloadend = function () {
// 返回base64位的文件内容
let url = reader.result
// 下载
window.location.href = url
}
// 开始读取指定的Blob中的内容。一旦完成,result属性中将包含一个data: URL格式的Base64字符串以表示所读取文件的内容。
reader.readAsDataURL(res)
}
方案3. 使用插件downloadjs
(1) 下载插件
bash
npm install --save downloadjs
插件地址:https://www.npmjs.com/package/downloadjs
(2)引入插件
js
import download from "downloadjs"
// 或者
const download = require('downloadjs')
(3) 使用
js
export const downloadFile = (res, type, filename) => {
// 将二进制流转成blob对象
const blob = new Blob([res], {
type: type
})
// 调用插件方法
download(blob, filename, type);
}