java

easypoi + spring boot + vue 实现 导出并下载 excel

开发中,导出 excel 是经常会遇到的,如果你使用 spring 框架,那么 easypoi 再适合不过了,它是对 Apache POI 的封装,但是使用起来却非常简单,唯一的缺点是包有点大,二十M左右,可能 Apache POI 本身就比较大吧,具体不清楚。

spring boot 集成 easypoi

由于有 easypoi-spring-boot-starter 所以集成非常简单,在你的 pom 文件里新增:

<dependency>
    <groupId>cn.afterturn</groupId>
    <artifactId>easypoi-spring-boot-starter</artifactId>
    <version>4.1.3</version>
</dependency>

至于版本号,你可以在 https://mvnrepository.com/artifact/cn.afterturn/easypoi-spring-boot-starter 查看最新版本。

然后,我们新建一个类,比如 VisitRecordModel.java 大致代码如下:

@Data
public class VisitRecordModel {

    @Excel(name = "标识", orderNum = "1")
    private String visitedFlag;

    @Excel(name = "计划回访时间", orderNum = "2", width = 12.0, exportFormat = "yyyy-MM-dd")
    private Date visitPlanDate;

}

然后 新建一个 EasyPoiUtil 类,代码如下:

public class EasyPoiUtil {

    public static void exportExcel(String title, String sheetName, boolean isCreateHeader,
                                   Class<?> pojoClass, List<?> data,
                                   HttpServletResponse response, String fileName) throws ExcelExportException {

        ExportParams exportParams = new ExportParams(title, sheetName);
        exportParams.setCreateHeadRows(isCreateHeader);

        Workbook workbook = ExcelExportUtil.exportExcel(exportParams, pojoClass, data);
        if (workbook == null) throw new ExcelExportException();

        try {
            downloadExcel(response, fileName, workbook);
        } catch (ExcelExportException e) {
            throw new ExcelExportException();
        }
    }

    private static void downloadExcel(HttpServletResponse response, String fileName, Workbook workbook) throws ExcelExportException {
        fileName = fileName  + ".xls";
        try {
            String encodeFileName = URLEncoder.encode(fileName, "UTF-8");
            response.setCharacterEncoding("UTF-8");
            response.setHeader("content-Type", "application/vnd.ms-excel");
            response.setHeader("Content-Disposition", "attachment;filename=" + encodeFileName);
            workbook.write(response.getOutputStream());
        } catch (Exception e) {
            throw new ExcelExportException();
        }
    }
}

这里的 download 方法支持 下载 中文的文件名哦,前提是你用 get 请求来下载,即 controller 层用 get 请求即可。调用如下:

private void downloadVisitRecord(ArrayList<HashMap<String, Object>> result, HttpServletResponse response) {
    List<VisitRecordModel> list = new ArrayList<>();
    for (HashMap<String, Object> map : result) {
        list.add(VisitRecordModel.fromMap(map));
    }
    try {
        EasyPoiUtil.exportExcel("xxxx - 回访记录", "回访记录", true,
                VisitRecordModel.class, list,
                response, "回访记录_" + DateUtils.formatDate(new Date(), "yyyy-MM-dd_HH-mm-ss"));
    } catch (ExcelExportException e) {
        throw new ExcelExportException();
    }
}

这里,传入 model 的 class 类型 以及 一个 list 数组,这个数组包含若干个 model 即可。如果使用 post 请求,那么 vue 部分代码需要修改,请求结束后,将返回保存为 blob 然后下载,即请求结束后代码如下:

const link = document.createElement("a");
let blob = new Blob([res], {
    type: "application/vnd.ms-excel"
});
link.style.display = "none";
link.href = URL.createObjectURL(blob);
link.setAttribute("download", "统计.xls");
document.body.appendChild(link);
link.click();
document.body.removeChild(link);

请求部分的代码也需要修改,具体如下:

return request({
    method: "post",
    url: "/xxx/xxx/export",
    data: params,
    responseType: "blob",
    headers: {
        "Content-Type": "multipart/form-data"
    }
})

如果请求部分代码不这样写,下载下来的 excel 会乱码哦,主要是 responseType 和 headers 吧!

full-stack-trip

Share
Published by
full-stack-trip
Tags: easypoi

Recent Posts

Android 自定义 View 入门

说来惭愧,工作数年,连基本的自…

4 年 ago

retrofit 同时支持 xml 和 json

retrofit 解析 jso…

4 年 ago

mysql - 存储过程 从入门到放弃

最近有个报表的需求,于是乎用了…

4 年 ago

奶嘴战略 - 你不得不知道的扎心真相(一)

一句:英雄枯骨无人问,戏子家事…

4 年 ago

acme.sh 的简单使用

acme.sh 是纯 shel…

4 年 ago

wrk -更现代化的http压测工具

wrk 是一款更现代化的 ht…

4 年 ago