在日常的工作開發中,Excel的匯入和匯出是必不可少的,如果自己寫相應的匯入匯出方法,會顯得十分繁瑣,本文采用Hutool工具類實現的Excel匯入匯出功能,可以大幅度減少今後開發中Excel的匯入匯出的相關操作。
提示:以下是本篇文章正文內容,下面案例可供參考
Hutool是一個小而全的Java工具類庫,通過靜態方法封裝,降低相關API的學習成本,提高工作效率,使Java擁有函數式語言般的優雅,讓Java語言也可以「甜甜的」。
Hutool中的工具方法來自於每個使用者的精雕細琢,它涵蓋了Java開發底層程式碼中的方方面面,它既是大型專案開發中解決小問題的利器,也是小型專案中的效率擔當;
Hutool是專案中「util」包友好的替代,它節省了開發人員對專案中公用類和公用工具方法的封裝時間,使開發專注於業務,同時可以最大限度的避免封裝不完善帶來的bug。
1.引入相關依賴
Java針對MS Office的操作的庫屈指可數,比較有名的就是Apache的POI庫。這個庫異常強大,但是使用起來也並不容易。Hutool針對POI封裝一些常用工具,使Java操作Excel等檔案變得異常簡單。Hutool-poi是針對Apache POI的封裝,因此需要使用者自行引入POI庫,Hutool預設不引入。
需要注意的是,hutool-4.x的poi-ooxml 版本需高於 3.17,hutool-5.x的poi-ooxml 版本需高於 4.1.2;本文使用的依賴資訊如下圖所示:
<!-- hutool工具類依賴-->
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.4.3</version>
</dependency>
<!--POI依賴,對office進行操作-->
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>4.1.2</version>
</dependency>
2.Excel匯出功能的實現
Hutool將Excel寫出封裝為ExcelWriter,原理為包裝了Workbook物件,每次呼叫merge(合併單元格)或者write(寫出資料)方法後只是將資料寫入到Workbook,並不寫出檔案,只有呼叫flush或者close方法後才會真正寫出檔案。由於機制原因,在寫出結束後需要關閉ExcelWriter物件,呼叫close方法即可關閉,此時才會釋放Workbook物件資源,否則帶有資料的Workbook一直會常駐記憶體。程式碼如下所示:
@RequestMapping(EXCEL_DOWNLOAD)
public void excelExport(HttpServletResponse httpServletResponse) throws IOException {
UserDTO userDTO = new UserDTO();
List<UserDTO> userDTOS = userService.selectUserDOBatch(userDTO);
//通過hutool工具建立的excel的writer,預設為xls格式
ExcelWriter writer = ExcelUtil.getWriter();
//設定要匯出到的sheet
writer.setSheet("表2");
writer.setSheet("表3");
//自定義excel標題和列名
writer.addHeaderAlias("id","使用者ID");
writer.addHeaderAlias("userName","使用者名稱");
writer.addHeaderAlias("loginPassword","密碼");
writer.addHeaderAlias("email","郵箱");
writer.addHeaderAlias("createDate","資料建立日期");
//合併單元格後的標題行,使用預設標題樣式
writer.merge(4,"使用者基本資訊表");
writer.renameSheet(0,"使用者登入資訊");
//一次性寫出內容,使用預設樣式,強制輸出標題
writer.write(userDTOS,true);
httpServletResponse.setContentType("application/vnd.ms-excel;charset=utf-8");
//name是下載對話方塊的名稱,不支援中文,想用中文名稱需要進行utf8編碼
String excelName = "使用者基本資訊表";
//excelName = new String(excelName.getBytes(),"utf-8");
excelName = URLEncoder.encode(excelName, "utf-8");
httpServletResponse.setHeader("Content-Disposition", "attachment;filename=" + excelName +".xls");
//將excel檔案資訊寫入輸出流,返回給呼叫者
ServletOutputStream excelOut = null;
try {
excelOut = httpServletResponse.getOutputStream();
writer.flush(excelOut,true);
} catch (IOException e) {
e.printStackTrace();
}finally {
writer.close();
}
IoUtil.close(excelOut);
}
以上匯出的Excel格式為.xls,如果想要匯出格式為.xlsx的excel檔案,只需修改上圖所示的相應位置程式碼即可,修改程式碼為:
//設定返回excel的格式為xlsx
httpServletResponse.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet;charset=utf-8");
httpServletResponse.setHeader("Content-Disposition","attachment;filename="+ URLEncoder.encode("使用者資訊表","utf-8") + ".xlsx");
生成的excel檔案如下如所示:
二、匯出Excel檔案
1.Excel讀取-ExcelReader
Excel檔案的匯入分為三種情況:
1.讀取Excel中所有行和列,都用列表表示
ExcelReader reader = ExcelUtil.getReader("d:/aaa.xlsx");
List<List<Object>> readAll = reader.read();
2.讀取為Map列表,預設第一行為標題行,Map中的key為標題,value為標題對應的單元格值。
ExcelReader reader = ExcelUtil.getReader("d:/aaa.xlsx");
List<Map<String,Object>> readAll = reader.readAll();
3.讀取為Bean列表,Bean中的欄位名為標題,欄位值為標題對應的單元格值。
ExcelReader reader = ExcelUtil.getReader("d:/aaa.xlsx");
List<Person> all = reader.readAll(Person.class);
本文Excel匯入讀取範例採用的是第三種方法實現,相關程式碼如下所示:
@RequestMapping(READ_EXCEL)
public void readExcel(){
ExcelReader reader = ExcelUtil.getReader("H:\\user.xlsx");
List<UserDTO> userDTOS = reader.readAll(UserDTO.class);
//紀錄檔輸出讀取到的資訊
log.info(userDTOS.toString());
}
其中UserDTO類的程式碼如下所示:
@Data
public class UserDTO {
@NotNull(message = "使用者id不能為空")
private Integer id;
@NotNull(message = "使用者名稱不能為空")
@Size(min = 4, max = 16, message = "使用者名稱長度錯誤")
private String userName;
@NotNull(message = "密碼不能為空")
@Size(min = 4, max = 16, message = "密碼長度錯誤")
private String loginPassword;
@NotNull(message = "郵箱不能為空")
@Email(message = "郵箱格式錯誤")
private String email;
@NotNull(message = "日期不能為空")
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
@JSONField(format = "yyyy-MM-dd HH:mm:ss")
private Date createDate;
}