本文使用的技术是Alibaba集团开源的EasyExcel技术,该技术是针对Apache POI技术的封装和优化,主要解决了POI技术的耗内存问题,并且提供了较好的API使用。
- 使用步骤繁琐
- 动态写出Excel操作非常麻烦
- 对于新手来说,很难在短时间内上手
- 读写时需要占用较大的内容,当数据量大时容器发生OOM
Maven依赖
<!-- easyexcel 依赖 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>easyexcel</artifactId>
<version>2.2.7</version>
</dependency>
EasyExcel API分析介绍
Ø EasyExcel入口类,用于构建开始各种操作
Ø ExcelReaderBuilder ExcelWriterBuilder 构建出一个 ReadWorkbook WriteWorkbook,可以理解成一个excel对象,一个excel只要构建一个
Ø ExcelReaderSheetBuilder ExcelWriterSheetBuilder 构建出一个 ReadSheet WriteSheet对象,可以理解成excel里面的一页,每一页都要构建一个
Ø ReadListener在每一行读取完毕后都会调用ReadListener来处理数据
Ø WriteHandler在每一个操作包括创建单元格、创建表格等都会调用WriteHandler来处理数据
Ø 所有配置都是继承的,Workbook的配置会被Sheet继承,所以在用EasyExcel设置参数的时候,在EasyExcel…sheet()方法之前作用域是整个sheet,之后针对单个sheet
EasyExcel 注解
Ø ExcelProperty 指定当前字段对应excel中的那一列。可以根据名字或者Index去匹配。当然也可以不写,默认第一个字段就是index=0,以此类推。千万注意,要么全部不写,要么全部用index,要么全部用名字去匹配。千万别三个混着用,除非你非常了解源代码中三个混着用怎么去排序的。
Ø ExcelIgnore 默认所有字段都会和excel去匹配,加了这个注解会忽略该字段
Ø DateTimeFormat 日期转换,用String去接收excel日期格式的数据会调用这个注解。里面的value参照java.text.SimpleDateFormat
Ø NumberFormat 数字转换,用String去接收excel数字格式的数据会调用这个注解。里面的value参照java.text.DecimalFormat
Ø ExcelIgnoreUnannotated 默认不加ExcelProperty 的注解的都会参与读写,加了不会参与
通用参数
Ø ReadWorkbook,ReadSheet 都会有的参数,如果为空,默认使用上级。
Ø converter 转换器,默认加载了很多转换器。也可以自定义。
Ø readListener 监听器,在读取数据的过程中会不断的调用监听器。
Ø headRowNumber 需要读的表格有几行头数据。默认有一行头,也就是认为第二行开始起为数据。
Ø head 与clazz二选一。读取文件头对应的列表,会根据列表匹配数据,建议使用class。
Ø clazz 与head二选一。读取文件的头对应的class,也可以使用注解。如果两个都不指定,则会读取全部数据。
Ø autoTrim 字符串、表头等数据自动trim
Ø password 读的时候是否需要使用密码
ReadWorkbook(理解成excel对象)参数
Ø excelType 当前excel的类型 默认会自动判断
Ø inputStream 与file二选一。读取文件的流,如果接收到的是流就只用,不用流建议使用file参数。因为使用了inputStream easyexcel会帮忙创建临时文件,最终还是file
Ø file 与inputStream二选一。读取文件的文件。
Ø autoCloseStream 自动关闭流。
Ø readCache 默认小于5M用 内存,超过5M会使用 EhCache,这里不建议使用这个参数。
ReadSheet(就是excel的一个Sheet)参数
Ø sheetNo 需要读取Sheet的编码,建议使用这个来指定读取哪个Sheet
Ø sheetName 根据名字去匹配Sheet,excel 2003不支持根据名字去匹配
注解
Ø ExcelProperty index 指定写到第几列,默认根据成员变量排序。value指定写入的名称,默认成员变量的名字,多个value可以参照快速开始中的复杂头
Ø ExcelIgnore 默认所有字段都会写入excel,这个注解会忽略这个字段
Ø DateTimeFormat 日期转换,将Date写到excel会调用这个注解。里面的value参照java.text.SimpleDateFormat
Ø NumberFormat 数字转换,用Number写excel会调用这个注解。里面的value参照java.text.DecimalFormat
Ø ExcelIgnoreUnannotated 默认不加ExcelProperty 的注解的都会参与读写,加了不会参与
参数
通用参数
Ø WriteWorkbook,WriteSheet ,WriteTable都会有的参数,如果为空,默认使用上级。
Ø converter 转换器,默认加载了很多转换器。也可以自定义。
Ø writeHandler 写的处理器。可以实现WorkbookWriteHandler,SheetWriteHandler,RowWriteHandler,CellWriteHandler,在写入excel的不同阶段会调用
Ø relativeHeadRowIndex 距离多少行后开始。也就是开头空几行
Ø needHead 是否导出头
Ø head 与clazz二选一。写入文件的头列表,建议使用class。
Ø clazz 与head二选一。写入文件的头对应的class,也可以使用注解。
Ø autoTrim 字符串、表头等数据自动trim
WriteWorkbook(理解成excel对象)参数
Ø excelType 当前excel的类型 默认xlsx
Ø outputStream 与file二选一。写入文件的流
Ø file 与outputStream二选一。写入的文件
Ø templateInputStream 模板的文件流
Ø templateFile 模板文件
Ø autoCloseStream 自动关闭流。
Ø password 写的时候是否需要使用密码
Ø useDefaultStyle 写的时候是否是使用默认头
WriteSheet(就是excel的一个Sheet)参数
Ø sheetNo 需要写入的编码。默认0
Ø sheetName 需要些的Sheet名称,默认同sheetNo
WriteTable(就把excel的一个Sheet,一块区域看一个table)参数
Ø tableNo 需要写入的编码。默认0
EasyExcel用法指南
简单的读取excel文件
public void read() {
String fileName = "demo.xlsx";
// 这里 需要指定读用哪个class去读,然后读取第一个sheet 文件流会自动关闭
// 参数一:读取的excel文件路径
// 参数二:读取sheet的一行,将参数封装在DemoData实体类中
// 参数三:读取每一行的时候会执行DemoDataListener监听器
EasyExcel.read(fileName, DemoData.class, new DemoDataListener()).sheet().doRead();
}
简单的写入excel文件
@Test
public void simpleWrite() {
String fileName = "demo.xlsx";
// 这里 需要指定写用哪个class去读,然后写到第一个sheet,名字为模板 然后文件流会自动关闭
// 如果这里想使用03 则 传入excelType参数即可
// 参数一:写入excel文件路径
// 参数二:写入的数据类型是DemoData
// data()方法是写入的数据,结果是List<DemoData>集合
EasyExcel.write(fileName, DemoData.class).sheet("模板").doWrite(data());
}
Web上传与下载
/**
excel文件的下载
*/
@GetMapping("download")
public void download(HttpServletResponse response) throws IOException {
response.setContentType("application/vnd.ms-excel");
response.setCharacterEncoding("utf-8");
response.setHeader("Content-disposition", "attachment;filename=demo.xlsx");
EasyExcel.write(response.getOutputStream(), DownloadData.class).sheet("模板").doWrite(data());
}
/**
excel文件的上传
*/
@PostMapping("upload")
@ResponseBody
public String upload(MultipartFile file) throws IOException {