vue利用流的方式下载Excel(附解决下载失败)

  1. 解决下载文件打不开 https://www.csdn.net/tags/MtTaMg4sNDcyMTgwLWJsb2cO0O0O.html

最主要是:导出文档,调用接口是设置 responseType: “blob” ,不能写在headers内,要单独设置。

Export(){
axios({
method: “get”,
url: xxxxxx,
responseType: “blob” , //必写
headers: {
‘token’: localStorage.getItem(‘token’)
}
}).then((res)=>{
//new blob对象,设置type为导出文件格式,这里以xls为列
let blob = new Blob([res.data],
{ type:‘application/vnd.ms-excel;charset=utf-8;’ }
);

    const link = document.createElement("a");  //创建a标签
    let fliaName = "xx.xls"
    link.style.display = "none";
    link.href = URL.createObjectURL(blob);
    link.download = fliaName;  //导出文件名
    document.body.appendChild(link);
    link.click();//执行下载
    URL.revokeObjectURL(link.href);  //释放url
    document.body.removeChild(link);  //释放标签
    this.$message.success('导出成功!');
  })
},
  1. 解决下载操作

https://blog.csdn.net/weixin_46381442/article/details/123779751

import axios from "axios"
import * as auth from '@/utils/auth.js'

let ajax = axios.create({
    baseURL: process.env.VUE_APP_BASE_API,
    timeout: 100000
});

ajax.interceptors.request.use(config => {
        config.headers = {
            Authorization: auth.getToken(),
            // OrgId: auth.getUser().orgId,
            // UserId: auth.getUser().id,
        }
        return config
    },
    err => {
        return Promise.reject(err)
    })

let downloadFile = async (url, formData, options) => {
    await ajax.post(url, formData, {responseType: 'arraybuffer'}).then(resp => download(resp, options))
}

let getFile = async (url, options) => {
    await ajax.get(url, {responseType: 'blob'}).then(resp => download(resp, options))
}

let download = (resp, options) => {
    let blob = new Blob([resp.data], {type: options.fileType ? options.fileType : 'application/octet-binary'})
    //创建下载的链接
    let href = window.URL.createObjectURL(blob)
    downloadBlob(href, options.fileName)
}

let downloadBlob = (blobUrl, fileName, revokeObjectURL) => {
    let downloadElement = document.createElement('a')
    downloadElement.href = blobUrl
    //下载后文件名
    downloadElement.download = fileName
    document.body.appendChild(downloadElement)
    //点击下载
    downloadElement.click()
    //下载完成移除元素
    document.body.removeChild(downloadElement)
    if (revokeObjectURL == null || revokeObjectURL) {
        //释放掉blob对象
        window.URL.revokeObjectURL(blobUrl)
    }
}

let getDownloadFileUrl = async (url, fileType) => {
    let blob
    await ajax.get(url, {responseType: 'blob'}).then(resp => {
        blob = new Blob([resp.data], {type: fileType ? fileType : 'application/octet-binary'});
    })
    return window.URL.createObjectURL(blob);
}

let getDownloadFileUrlByPost = async (url, data, fileType) => {
    let blob
    await ajax.post(url, data, {responseType: 'blob'}).then(resp => {
        blob = new Blob([resp.data], {type: fileType ? fileType : 'application/octet-binary'});
    })
    return window.URL.createObjectURL(blob);
}

let getDownloadFileBlob = async (url, fileType) => {
    let blob
    await ajax.get(url, {responseType: 'blob'}).then(resp => {
        blob = new Blob([resp.data], {type: fileType ? fileType : 'application/octet-binary'});
    })
    return blob;
}

export default {
    ajax,
    downloadFile,
    getFile,
    getDownloadFileUrl,
    getDownloadFileUrlByPost,
    getDownloadFileBlob,
    downloadBlob
}


调用:
//先引用

import ajax from '../../utils/ajax.js'
//使用
ajax.downloadFile('URL',null,{下载的文件名称})
<think>我们被要求使用中文回答,并且按照给定的格式规范。用户的问题是关于在Vue中实现点击按钮下载Excel文件的方法。根据提供的引用,我们可以总结出几种方法: 方法1:使用原生的Blob对象和URL.createObjectURL(如引用[1]和[4]所示) 步骤: 1. 发起请求时设置响应类型为blob(responseType: 'blob') 2. 在请求成功的回调中,将返回的数据转换为Blob对象,指定类型为Excel类型 3. 创建一个临时的a标签,设置其href为Blob对象的URL,并设置download属性为文件名 4. 触发a标签的点击事件,然后移除a标签 方法2:使用第三方库vue-json-excel(如引用[2]和[3]所示) 步骤: 1. 安装vue-json-excel 2. 在main.js中引入并注册组件 3. 在模板中使用<download-excel>组件,通过绑定数据(json_data)和字段映射(json_fields)来导出Excel 用户的问题没有提到需要导出JSON数据,而是下载一个Excel文件(可能是从后端接口返回的文件),所以方法1更通用。但用户也可能需要将页面上的数据导出为Excel,这时方法2更方便。 考虑到用户可能有两种需求: 1. 从后端接口下载一个已经存在的Excel文件(比如模板或报表) 2.前端的数据(如表格数据)导出为Excel 因此,我们可以分别介绍这两种情况。 另外,引用[4]中提到了一个封装的download方法,但这里我们也可以使用类似引用[1]的方法。 下面我们给出两种实现方式: ### 方式一:通过后端接口下载Excel文件文件) 这种方法适用于后端返回文件的情况。 1.Vue组件中,创建一个按钮,并绑定一个方法(例如`exportExcel`)。 2. 在`exportExcel`方法中,使用axios(或其他HTTP库)调用后端接口,注意设置`responseType: 'blob'`。 3. 在请求成功后,将返回的数据转换为Blob对象,然后创建一个临时的下载链接并触发下载。 示例代码: ```vue <template> <button @click="exportExcel">下载Excel文件</button> </template> <script> import axios from 'axios'; export default { methods: { exportExcel() { // 注意:根据实际情况修改接口地址和参数 axios({ url: '/api/download-excel', // 接口地址 method: 'get', // 或 'post',根据后端要求 responseType: 'blob', // 重要:设置响应类型为blob // 如果有参数,可以放在params(GET)或data(POST)中 // params: { ... } }).then(response => { // 创建一个Blob对象,设置类型为Excel const blob = new Blob([response.data], { type: 'application/vnd.ms-excel' }); // 创建下载链接 const downloadUrl = URL.createObjectURL(blob); const link = document.createElement('a'); link.href = downloadUrl; // 设置下载文件link.download = '文件.xlsx'; document.body.appendChild(link); link.click(); // 清理:移除链接和释放URL对象 document.body.removeChild(link); URL.revokeObjectURL(downloadUrl); }).catch(error => { console.error('下载失败', error); }); } } } </script> ``` ### 方式二:使用vue-json-excel组件导出前端数据 这种方法适用于将当前Vue组件中的数据导出为Excel文件。 1. 安装vue-json-excel: ```bash npm install vue-json-excel --save ``` 2. 在main.js中注册组件: ```javascript import Vue from 'vue'; import JsonExcel from 'vue-json-excel'; Vue.component('downloadExcel', JsonExcel); ``` 3. 在组件中使用: ```vue <template> <download-excel :data="json_data" :fields="json_fields" name="导出文件.xls" type="xls" > <button>导出为Excel</button> </download-excel> </template> <script> export default { data() { return { json_fields: { '姓名': 'name', '年龄': 'age', // 可以指定字段名,键是Excel列标题,值是数据对象的属性 }, json_data: [ { name: '张三', age: 20 }, { name: '李四', age: 25 }, // ... 数据数组 ] }; } }; </script> ``` 注意:vue-json-excel默认导出的是xls格式(使用旧的Excel格式),如果需要xlsx,可能需要使用其他库或修改配置。 ### 对比 - 方式一适用于从后端获取文件(比如生成的报表)并下载。 - 方式二适用于将前端已有的数据(如表格数据)导出为Excel。 用户可以根据实际需求选择合适的方法。 ### 相关问题 1. 如何解决Excel文件下载后打开乱码的问题? 2. 如何实现大文件的分块下载和断点续传? 3. 如何在前端生成复杂的Excel文件(如合并单元格、样式等)? 4. 如何实现下载进度条的显示? 5. 使用vue-json-excel导出大量数据时如何避免页面卡顿?</think>在 Vue.js 中实现点击按钮下载 Excel 文件,主要有两种常用方法:使用原生 JavaScript Blob 对象或借助第三方库(如 vue-json-excel)。以下是详细实现方案: --- ### 方法一:使用原生 Blob 对象(推荐) 通过后端接口获取文件利用 Blob 对象创建下载链接。适用于从后端下载生成的 Excel 文件。 ```vue <template> <button @click="downloadExcel">下载Excel文件</button> </template> <script> import axios from 'axios'; export default { methods: { async downloadExcel() { try { // 调用后端接口,设置 responseType: 'blob' const response = await axios.get('/api/download-excel', { responseType: 'blob', // 关键:声明响应类型为二进制 }); // 创建 Blob 对象(指定 Excel MIME 类型) const blob = new Blob([response.data], { type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' }); // 创建临时下载链接 const downloadUrl = URL.createObjectURL(blob); const link = document.createElement('a'); link.href = downloadUrl; link.download = '数据报表.xlsx'; // 设置文件link.style.display = 'none'; // 触发下载 document.body.appendChild(link); link.click(); // 清理资源 document.body.removeChild(link); URL.revokeObjectURL(downloadUrl); } catch (error) { console.error('下载失败:', error); alert('文件下载失败,请重试'); } } } }; </script> ``` #### 关键点说明: 1. **`responseType: 'blob'`**:必须在请求中声明,确保正确接收二进制[^1][^4] 2. **Blob 类型**: - `.xlsx` 文件:`application/vnd.openxmlformats-officedocument.spreadsheetml.sheet` - `.xls` 文件:`application/vnd.ms-excel` 3. **文件名设置**:通过 `link.download` 属性自定义下载文件名 4. **资源清理**:下载后需移除临时链接释放内存 --- ### 方法二:使用 vue-json-excel 库 适用于将前端数据直接导出为 Excel(无需后端接口),需提前安装依赖。 #### 安装依赖 ```bash npm install vue-json-excel ``` #### 组件实现 ```vue <template> <download-excel :data="tableData" :fields="excelFields" name="用户数据.xls" type="xls" > <button>导出Excel</button> </download-excel> </template> <script> import DownloadExcel from 'vue-json-excel'; export default { components: { DownloadExcel }, data() { return { // 表格数据 tableData: [ { id: 1, name: '张三', age: 28 }, { id: 2, name: '李四', age: 32 } ], // Excel 列映射(键:Excel列名,值:数据字段) excelFields: { '用户ID': 'id', '姓名': 'name', '年龄': 'age' } }; } }; </script> ``` #### 参数说明: | 参数 | 说明 | |----------|----------------------------------------------------------------------| | `data` | 需要导出的数据数组(支持嵌套对象)[^2][^3] | | `fields` | 字段映射关系(控制 Excel 列顺序和标题) | | `name` | 下载文件名(默认扩展名 .xls) | | `type` | 文件类型(`xls` 或 `csv`) | --- ### 常见问题解决 1. **文件乱码**:确保请求设置 `responseType: 'blob'`[^1][^4] 2. **文件名中文乱码**:将文件名编码为 UTF-8: ```javascript link.download = encodeURIComponent('中文文件.xlsx'); ``` 3. **大文件下载**:使用分片下载或进度提示优化用户体验 4. **跨域问题**:确保后端配置 CORS 头部(`Access-Control-Allow-Origin`) --- ### 两种方案对比 | 特性 | 原生 Blob 方案 | vue-json-excel 方案 | |--------------------|-----------------------------------|----------------------------------| | 适用场景 | 后端返回文件 | 前端数据直接导出 | | 依赖项 | 无 | 需安装第三方库 | | 文件类型 | 支持任意格式(Excel/PDF/图片等) | 仅支持 Excel/CSV | | 复杂格式支持 | 高(依赖后端生成) | 低(仅基础表格) | | 前端数据处理压力 | 小 | 大(数据量大时可能卡顿) | 根据实际需求选择方案: - 需下载服务器生成的文件(如报表)→ **原生 Blob 方案** - 需导出前端页面数据 → **vue-json-excel 方案** --- ### 相关问题 1. 如何实现 Excel 文件上传并解析数据到 Vue 组件? 2. 下载文件时如何显示进度条? 3. 如何封装通用的文件下载工具函数? 4. 前端导出 Excel 时如何处理复杂样式(合并单元格/字体颜色)? 5. 如何解决跨域下载文件时的身份验证问题? > 引用说明: > [^1]: 使用 Blob 和 responseType: 'blob' 处理文件下载 > [^2]: vue-json-excel 库的安装和组件注册方法 > [^3]: 通过字段映射控制 Excel 列标题和数据来源 > [^4]: 必须设置 responseType: 'blob' 避免文件乱码
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值