EasyExcel 导出简单应用,简单模板导出

EasyExcel 导出简单应用(文章末附demo下载地址)

应用场景: 主从表单中,用户想定制excel导出数据。看过一点Apache poi,一般人上手还是要花一些时间,且Apache poi做Excel的一些处理存在内存溢出等缺陷。相对于Apache poi存在明显的优势就是上手块,且内存占用小,故采用EasyExcel。
EasyExcel官网

基于EasyExcel实现Excel导出下载

准备:
  1. SpringBoot + JPA + lombok
  2. EasyExcel(最新maven依赖)
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>easyexcel</artifactId>
            <version>3.1.2</version>
        </dependency> 
  1. 数据库Mysql
  2. Student学生表 (建表sql)
CREATE TABLE `student` (
  `id` bigint NOT NULL AUTO_INCREMENT,
  `username` varchar(100) DEFAULT NULL,
  `age` int DEFAULT NULL,
  `attendtime` datetime DEFAULT NULL,
  `address` varchar(256) DEFAULT NULL,
  `schoolclass` int DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci

  1. Excel模板文件
    模板下载
    QQ截图20221104130258.png
    模板参数说明:
  • 大括号“{}” 引用的参数就是后面导出Excel需要填充的参数
  • 英文句号“.”表示该填充数据可能多条,则此时会自动填充换行
  • Excel中样式(行高 列宽等)及颜色会在导出时一并设置成和模板一致(这种调试样式就可以直接在Excel中进行调试,再将模板放到服务器指定位置,避免在代码中进行繁琐的样式设置操作)

相关类说明

1. Student基类
@Data
@ToString
@AllArgsConstructor
@NoArgsConstructor
@Entity
@Table(name = "student")
public class Student implements Serializable {

    /**
     * 主键id也是序号,由于数据库序号设置的自增
     */
    @GeneratedValue(strategy= GenerationType.IDENTITY)
    @Id
    private Long id;
    private String username;
    private int age;
    /**
     * 入学时间,设置java.sql.Timestamp类型,便于后面自定义Convert类时对格式进行转换
     */
    private Timestamp attendtime;
    private String address;
    private int schoolclass;

}

:@GeneratedValue(strategy= GenerationType.IDENTITY) 采用数据库ID自增长的方式来自增主键字段

2. 构造导出Excel方法
    /**
     * 设置web响应输出的文件名称
     * @param response web响应
     * @param fileName 导出文件名称
     */
    private static void setResponseHeader(HttpServletResponse response, String fileName) {
        response.reset();
        response.setContentType("application/vnd.ms-excel;charset=utf-8");
        try {
            response.setHeader("Content-Disposition", "attachment;filename=" +
                    URLEncoder.encode(fileName + ".xlsx", "UTF-8"));
        } catch (UnsupportedEncodingException e) {
            log.error("不支持的编码", e.getLocalizedMessage());
        }
        response.setCharacterEncoding("UTF-8");
    }

    public static void exportStudedntExcel(HttpServletResponse response, HashMap<String,Object> datas,String fileName) throws IOException{


        setResponseHeader(response, fileName);
        //未获取到数据时
        if (datas.get("data") == null){
            return;
        }
        ExcelWriter workbook= null;
        BufferedOutputStream bos = new BufferedOutputStream(response.getOutputStream());
        try{
            String template="student_fill_template.xlsx";
            //日期转化格式字符串
            TimestampStringConverter converter = new TimestampStringConverter();
            workbook = EasyExcel.write(bos).registerConverter(converter).withTemplate(template).build();

            WriteSheet sheet = EasyExcel.writerSheet("Sheet1").build();
            FillConfig fillConfig = FillConfig.builder().forceNewRow(true).build();

            //填充议题数据
            workbook.fill(datas.get("data"),fillConfig,sheet);

            //datas.remove("data");
            //获取副标题及角标
            HashMap<String,Object> map = new LinkedHashMap<>();
            map.put("schoolclass",datas.get("schoolclass"));
            map.put("exporttime",datas.get("exporttime"));
            //填充角标及标题数据
            workbook.fill(map,sheet);
        }catch (Throwable ex){
            log.error("exportMeetExcel",ex.getMessage());
        }finally {
            bos.flush();
            if (workbook != null){
                workbook.finish();
            }
        }
    }
  • setResponseHeader 设置Excel下载的请求头格式及文件名
  • workbook = EasyExcel.write(bos, Student.class).withTemplate(template).build();
  • withTemplate(template) 根据模板Excel构造一个工作簿
  • .build() 构造生成ExcelWriter时要手动释放资源,而不使用build生成的ExcelWriterBuilder对象会自动释放资源,这里使用ExcelWriter对象是因为此deno中到向模板填充的数据需要多次进行填充,若使用ExcelWriterBuilder一次使用后就自动释放资源,导致后面的填充失败!
  • TimestampStringConverter 自定义对象见下一节
  • FillConfig 对象用于填充数据时的一些设置,比如此处,由于学生信息数据行是多行数据,forceNewRow(true)作用是在末尾新增,如若不进行此项操作,则最后一行的导出时间填充时会覆盖模板位置的值

3.Timestamp日期格式自定义转换器类TimestampStringConverter

public class TimestampStringConverter implements Converter<Timestamp> {

    @Override
    public Class<?> supportJavaTypeKey() {
        return Timestamp.class;
    }

    @Override
    public CellDataTypeEnum supportExcelTypeKey() {
        return CellDataTypeEnum.STRING;
    }


    @Override
    public WriteCellData<?> convertToExcelData(Timestamp value, ExcelContentProperty contentProperty,
                                               GlobalConfiguration globalConfiguration) {
        WriteCellData cellData = new WriteCellData();
        String cellValue;
        if (contentProperty == null || contentProperty.getDateTimeFormatProperty() == null) {
            cellValue = DateUtils.format(value.toLocalDateTime(), "yyyy年MM月dd日", globalConfiguration.getLocale());
        } else {
            cellValue = DateUtils.format(value.toLocalDateTime(), contentProperty.getDateTimeFormatProperty().getFormat(),
                    globalConfiguration.getLocale());
        }
        cellData.setType(CellDataTypeEnum.STRING);
        cellData.setStringValue(cellValue);
        cellData.setData(cellValue);
        return cellData;
    }
}
  • convertToExcelData 方法中 value为数据中为Timestamp类型的值,此处我获取Timestamp 将时间戳转化为yyyy年MM月dd日的字符串格式,在创建工作簿的时候使用registerConverter将转换器注册到工作簿中。
  • 若只想转换该类型的某个实体属性的值,可以借助 @ExcelProperty 注解,添加 converter 属性,如:
	@ExcelProperty(value = "入学时间", converter = TimestampStringConverter.class)
        private Timestamp attendtime;

工程创建说明

该工程是基于SpringBoot + Jpa的一个从数据库导出Excel的案例,所以在创建工程时可以直接通过Spring Initializr创建一个web工程并导入对应包

本工程目录说明
image.png
student_fill_template.xlsx 为Excel模板,注意放置位置

该工程有两个接口
POST:http://127.0.0.1:8080/init 向student表中初始化学生信息
GET:http://127.0.0.1:8080/export/{classno} 从学生student表中导出学生信息以excel的形式保存,其中classno是班级编号,1-9,对应枚举如下:

    One("高一一班",1),Two("高一二班",2),Three("高一三班",3),
    Four("高二一班",4),Five("高二二班",5),Six("高二三班",6),
    Seven("高三一班",5),Eight("高三二班",8),Nine("高三三班",9);

demo下载地址

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值