1.后端代码
java
//权限管理部分注解
@RequiresPermissions("admin:goods:InventoryExport")
@RequiresPermissionsDesc(menu = {"商品管理", "商品管理"}, button = "库存导出")
@GetMapping("/inventoryExport")
public void export(HttpServletResponse response, Integer goodsId, String goodsSn, String name, Integer catId) throws IOException {
//查询数据
List<Goods> export = adminGoodsService.export(goodsId, goodsSn, name, catId);
ExcelWriter excelWriter = ExcelUtil.getWriter(true);
excelWriter.addHeaderAlias("id", "商品id");
//将数据模型中的username字段映射为Excel表格中的用户名列。
excelWriter.addHeaderAlias("productId", "库存id");
excelWriter.addHeaderAlias("name", "商品名称");
excelWriter.addHeaderAlias("name", "商品名称");
excelWriter.setOnlyAlias(true);
excelWriter.write(export, true);
String fileName = URLEncoder.encode("库存导出.xlsx", "UTF-8");
try {
response.setHeader("Content-Disposition", "attachment;filename=" + fileName + ".xlsx");
ServletOutputStream outputStream = response.getOutputStream();
excelWriter.flush(outputStream, true);
outputStream.close();
excelWriter.close();
} catch (IOException e) {
e.printStackTrace();
}
}
2.前端代码
javascript
handleDownload() {
this.downloadLoading = true
//请求后端接口
InventoryExport().then(response => {
//临时创建一个a标签然后点击进行下载
const url = window.URL.createObjectURL(new Blob([response.data]));
const link = document.createElement('a');
link.href = url;
link.setAttribute('download', '库存导出.xlsx');
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
this.downloadLoading = false
}).catch(response => {
this.$notify.error({
title: '失败',
message: response.data.errmsg
})
})
}
//request封装代码
export function InventoryExport(query) {
return request({
url: '/goods/inventoryExport',
method: 'get',
params: query,
responseType: 'blob',
})
}
3.注意点
刚开始前端代码请求到后端接口后老是只走catch不走then
经过原因排查之后是因为前端请求拦截器的原因,接口没有返回自定义状态码就会走catch,
但是导出接口返回的是blob数据没有状态码,所以需要在拦截器中加入以下代码:
javascript
service.interceptors.response.use(
response => {
//文件流不检测自定义状态码
if(response.config.responseType==="arraybuffer" || response.config.responseType==="blob" || response.data instanceof Blob) {
return response; // 文件流
}
const res = response.data
if (res.errno === 501) {
MessageBox.alert('系统未登录,请重新登录', '错误', {
confirmButtonText: '确定',
type: 'error'
}).then(() => {
store.dispatch('FedLogOut').then(() => {
location.reload()
})
})
return Promise.reject('error')
} else if (res.errno === 502) {
...
}
})