基于Spring+poi和Vue导出EXCEL表格

633 阅读2分钟

这是我参与8月更文挑战的第1天,活动详情查看:8月更文挑战

  • 最近项目遇到一个excel报表导出的功能。因为报表最初是通过vue+table由前端进行渲染所以打算通过前端操作进行excel表格的导出,但是结果不理想(excel总是不能以页面展示的table样式进行导出)应该是自己太菜了,于是想到后端可以预设excel模板进行excel的生成导出,于是就有了如下demo。
  1. 配置poi依赖
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi</artifactId>
    <version>3.17</version>
</dependency>

<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml</artifactId>
    <version>3.17</version>
</dependency>
  1. 保存模板文件 我放在项目resource文件夹下,注意引用路径。

!!!不要直接修改文件后缀会报错,建议通过另存为修改文件后缀,建议使用xlsx后缀excel。!!!

image.png

注意demo的名称所在列为AB两列合并

image.png 3. 后端业务实现

demo展示两种赋值方式:指定单元格赋值和批量赋值。

@GetMapping("/exportExcel")
@ApiOperation("Excel导出")
public Result exportExcel(HttpServletResponse response) throws Exception {
    try {
        ClassPathResource cpr = new ClassPathResource("/templates/"+"demo.xlsx");
        InputStream is = cpr.getInputStream();
        Workbook workbook = new XSSFWorkbook(is);
        org.apache.poi.ss.usermodel.Sheet sheet0 =workbook.getSheetAt(0);
        //指定行
        Row row = sheet0.getRow(2); //第三行
        //指定列,因为名称所在列为两列合并所以数据1为第三列
        Cell cell = row.getCell(2); //第三列
        //赋值
        cell.setCellValue("data1-1");
        //批量赋值
        for(int i = 0;i<2;i++){
            Row row1 = sheet0.getRow(i+3);//从第4行开始填充数据
            Cell cell1 = row1.getCell(2); //第三列
            cell1.setCellValue("data"+i);
        }
        String fileName = "demo.xlsx";
        downLoadExcel(fileName, response, workbook);
        return ResultUtil.success();
    } catch (Exception e) {
        e.printStackTrace();
        throw new Exception("导出信息失败!");
    }
}
           
//处理方法
public static void downLoadExcel(String fileName, HttpServletResponse response, Workbook workbook) {
    try {
        response.setCharacterEncoding("UTF-8");
        response.setHeader("content-Type", "application/vnd.ms-excel");
        response.setHeader("Content-Disposition",
                "attachment;filename="" + URLEncoder.encode(fileName, "UTF-8") + """);
        workbook.write(response.getOutputStream());
    } catch (IOException e) {
        e.printStackTrace();
    }
}
  1. 前端业务实现 数据请求,注意responseType必须填写
export function exportExcel() {
  return request({
    url: '/report/exportExcel',
    method: 'get',
    responseType: 'blob'
  })
}

数据导出

async exportExcelTest() {
  const res = await exportExcel();
  const link = document.createElement('a')
  let blob = new Blob([res.data], {type: 'application/vnd.ms-excel'})
  link.style.display = 'none'
  link.href = URL.createObjectURL(blob)
  link.download = "导出测试"//下载的文件名
  document.body.appendChild(link)
  link.click()
  document.body.removeChild(link)
}
  1. 效果展示

image.png