Easy Excel 的使用說明
官方文檔地址1:https://www.yuque.com/easyexcel/doc
官方文檔地址2:https://alibaba-easyexcel.github.io/index.html
<dependency> <groupId>com.alibaba</groupId> <artifactId>easyexcel</artifactId> <version>3.0.5</version> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <version>1.18.20</version> </dependency>
02 寫excel文件
數據的實體類
@Data @TableName("excel_user") public class ExcelUser { @TableId(value = "id", type = IdType.AUTO) @ExcelIgnore private Long id; @ExcelProperty("姓名") private String name; @ExcelProperty("年齡") private Integer age; @ExcelProperty("身高") private Double height; }
寫excel的方法
/** * 寫excel文件 * @param excelFile * 導出的文件路徑(測試用絕對地址) * @param ignoreFiledNames * 忽略的字段 * @param template * 數據模板(數據的class) * @param sheetName * sheet名 * @param data * 數據 */ public static void writeExcel(String excelFile, Set<String> ignoreFiledNames, Class template, String sheetName, List<?> data) { ExcelWriterBuilder builder = EasyExcel.write(excelFile, template); if (ignoreFiledNames != null) { builder.excludeColumnFiledNames(ignoreFiledNames); } builder.sheet(sheetName).doWrite(data); }
03 文件的下載
@GetMapping("/download") public void download(String filename,HttpServletResponse response) { ExcelFileUtils.downLoadFile(response,filename); }
下載的方法
/** * 下載文件 * * @param response * 相應response * @param filePath * 文件路徑 */ public static void downLoadFile(HttpServletResponse response, String filePath) { if (StringUtils.isBlank(filePath)) { return; } File file = new File(filePath); if (!file.exists()) { return; } OutputStream out = null; try { response.reset(); response.setContentType("application/octet-stream; charset=utf-8"); response.setHeader("Content-Disposition", "attachment; filename=" + file.getName()); out = response.getOutputStream(); out.write(Files.readAllBytes(file.toPath())); out.flush(); } catch (IOException e) { e.printStackTrace(); } finally { if (out != null) { try { out.close(); } catch (IOException e) { e.printStackTrace(); } } } }
04 文件的上傳
package com.saiyou.entity; import com.alibaba.excel.context.AnalysisContext; import com.alibaba.excel.event.AnalysisEventListener; import com.alibaba.fastjson.JSON; import com.saiyou.service.ExcelUserService; import lombok.extern.slf4j.Slf4j; import java.util.ArrayList; import java.util.List; /** * @author : lyn * 技術點 : * @description: excel 的監聽器 * @date : 2021/12/4 14:43 */ @Slf4j public class ExcelUserListener extends AnalysisEventListener<ExcelUser> { /** * 每隔5條存儲數據庫,實際使用中可以3000條,然后清理list ,方便內存回收 */ private static final int BATCH_COUNT = 5; List<ExcelUser> list = new ArrayList<ExcelUser>(); /** * 假設這個是一個DAO,當然有業務邏輯這個也可以是一個service。當然如果不用存儲這個對象沒用。 */ private ExcelUserService excelUserService; public ExcelUserListener(){} /** * 如果使用了spring,請使用這個構造方法。每次創建Listener的時候需要把spring管理的類傳進來 * * @param excelUserService */ public ExcelUserListener(ExcelUserService excelUserService) { this.excelUserService = excelUserService; } /** * 這個每一條數據解析都會來調用 * * @param data * one row value. Is is same as {@link AnalysisContext#readRowHolder()} * @param context */ @Override public void invoke(ExcelUser data, AnalysisContext context) { log.info("解析到一條數據:{}", JSON.toJSONString(data)); list.add(data); // 達到BATCH_COUNT了,需要去存儲一次數據庫,防止數據幾萬條數據在內存,容易OOM if (list.size() >= BATCH_COUNT) { saveData(); // 存儲完成清理 list list.clear(); } } /** * 所有數據解析完成了 都會來調用 * * @param context */ @Override public void doAfterAllAnalysed(AnalysisContext context) { // 這里也要保存數據,確保最后遺留的數據也存儲到數據庫 saveData(); log.info("所有數據解析完成!"); } /** * 加上存儲數據庫 */ private void saveData() { log.info("{}條數據,開始存儲數據庫!", list.size()); //調用service保存到數據庫 excelUserService.saveBatch(list); log.info("存儲數據庫成功!"); } }
controller接口
@Autowired private ExcelUserService excelUserService; /** * 文件上傳 * <p>1. 創建excel對應的實體對象 參照{@link ExcelUser} * <p>2. 由於默認一行行的讀取excel,所以需要創建excel一行一行的回調監聽器, * <p>3. 直接讀即可 */ @PostMapping("/upload") public String upload(MultipartFile file) throws IOException { EasyExcel.read(file.getInputStream(), ExcelUser.class, new ExcelUserListener(excelUserService)).sheet().doRead(); return "success"; }
需要自己補充service和mapper
package com.saiyou.utils; import com.alibaba.excel.EasyExcel; import com.alibaba.excel.write.builder.ExcelWriterBuilder; import com.baomidou.mybatisplus.core.toolkit.StringUtils; import com.saiyou.entity.ExcelUser; import com.saiyou.entity.ExcelUserListener; import lombok.extern.slf4j.Slf4j; import javax.servlet.http.HttpServletResponse; import java.io.File; import java.io.IOException; import java.io.OutputStream; import java.nio.file.Files; import java.util.Arrays; import java.util.List; import java.util.Set; /** * @author : lyn * 技術點 : * @description: excel的讀寫,上傳和下載 * @date : 2021/12/4 13:50 */ @Slf4j public class ExcelFileUtils { /** * 寫excel文件 * @param excelFile * 導出的文件路徑 * @param ignoreFiledNames * 忽略的字段 * @param template * 數據模板 * @param sheetName * sheet名 * @param data * 數據 */ public static void writeExcel(String excelFile, Set<String> ignoreFiledNames, Class template, String sheetName, List<?> data) { ExcelWriterBuilder builder = EasyExcel.write(excelFile, template); if (ignoreFiledNames != null) { builder.excludeColumnFiledNames(ignoreFiledNames); } builder.sheet(sheetName).doWrite(data); } /** * 讀取excel文件,不能通用嗎? * @param fileName */ public static void readExcel(String fileName) { // 這里 需要指定讀用哪個class去讀,然后讀取第一個sheet 文件流會自動關閉 EasyExcel.read(fileName, ExcelUser.class, new ExcelUserListener() ).sheet().doRead(); } /** * 下載文件 * * @param response * 相應response * @param filePath * 文件路徑 */ public static void downLoadFile(HttpServletResponse response, String filePath) { if (StringUtils.isBlank(filePath)) { return; } File file = new File(filePath); if (!file.exists()) { return; } OutputStream out = null; try { response.reset(); response.setContentType("application/octet-stream; charset=utf-8"); response.setHeader("Content-Disposition", "attachment; filename=" + file.getName()); out = response.getOutputStream(); out.write(Files.readAllBytes(file.toPath())); out.flush(); } catch (IOException e) { e.printStackTrace(); } finally { if (out != null) { try { out.close(); } catch (IOException e) { e.printStackTrace(); } } } } public static void main(String[] args) { ExcelUser user = new ExcelUser(); user.setName("李四"); user.setAge(56); user.setHeight(126.6); writeExcel("D:/excel-test.xlsx",null,ExcelUser.class,"表一", Arrays.asList(user)); } }