【POI】Excel資料匯入
阿新 • • 發佈:2021-11-03
Postman請求方式:
Controller介面程式碼:
/** * /partImport/part/importUpload * @param importFile * @return */ @PostMapping("/part/importUpload") public Map<String, Object> importUpload(@RequestParam(value = "file") MultipartFile importFile) { return partMainDataImportService.importUpload(importFile); }
物件型別:
import org.springframework.web.multipart.MultipartFile;
邏輯思路:
1、Excel轉變可獲取資料
2、資料結果集插入DB
@Override public Map<String, Object> importUpload(MultipartFile importFile) { StopWatch stopWatch = new StopWatch(); stopWatch.start(); Map<String, Object> resultMap = newHashMap<>(); List<Map<Integer, String>> partMainDatas = null; // Sheet1 配件主資料資訊 List<Map<Integer, String>> partExclusivePrice = null; // Sheet2 配件專屬價格 List<Map<Integer, String>> partReplacements = null; // Sheet3 配件替換件 try {// 獲取資料集合物件 getDataListFromImportExcel匯出方法 partMainDatas = getDataListFromImportExcel(importFile, resultMap, 0); partExclusivePrice = getDataListFromImportExcel(importFile, resultMap, 1); partReplacements = getDataListFromImportExcel(importFile, resultMap, 2); Integer integer = insertPartMainData(partMainDatas); resultMap.put("partMainDatas", integer); if (!CollectionUtils.isEmpty(partExclusivePrice)) { Integer integer2 = insertExclusivePrice(partExclusivePrice); resultMap.put("partOwnPrices", integer2); } else { resultMap.put("partOwnPrices", 0); } if (!CollectionUtils.isEmpty(partReplacements)) { Integer integer3 = insertReplacements(partReplacements); resultMap.put("partShifts", integer3); } else { resultMap.put("partShifts", 0); } } catch (Exception exception) { exception.printStackTrace(); return resultMap; } finally { stopWatch.stop(); resultMap.put("execTime", stopWatch.getTotalTimeSeconds() + '秒'); } resultMap.put("200", "匯入成功"); return resultMap; }
Excel轉換到資料邏輯部分:
/** * 提供給配件主資料匯入處理 * @param importFile * @param map 響應結果,如果報錯異常,則在這裡設定 * @return */ private List<Map<Integer, String>> getDataListFromImportExcel(MultipartFile importFile, Map<String, Object> map, Integer sheetIndex) throws Exception { Workbook workbook = null; // Excel工作薄 Sheet sheet = null; // Excel表單 Sheet頁 Row row = null; // 行 Map<Integer, String> dataMap = null; // 表單中的一行資料 List<Map<Integer, String>> dataList = null; // 表單中的所有資料 boolean isValidRow = false; // Excel行中是否是有效資料行 InputStream inputStream = importFile.getInputStream(); // 檔案流 String filename = importFile.getOriginalFilename(); // 檔名 // 獲取Excel工作簿物件 if ("xls".equalsIgnoreCase(filename.substring(filename.lastIndexOf(".") + 1, filename.length()))) { workbook = new HSSFWorkbook(inputStream); } else { workbook = new XSSFWorkbook(inputStream); } sheet = workbook.getSheetAt(sheetIndex); // 獲取指定Sheet頁來處理 Boolean flag = false; // 標記,如果檢測到空行為true Integer num = 0; dataList = new ArrayList<>(); int physicalNumberOfRows = sheet.getPhysicalNumberOfRows(); for (int i = 1 /* 從表單第二行開始讀取資料,讀取整個表單中的資料 */; i < physicalNumberOfRows; i++) { num = 0; if(flag){ break; } row = sheet.getRow(i); if (null != row) { dataMap = new HashMap<>(); int physicalNumberOfCells = sheet.getRow(0).getPhysicalNumberOfCells(); for (int j = 0; j < physicalNumberOfCells; j++) { if(null != row.getCell(j) && !StringUtils.isNullOrEmpty(row.getCell(j).getStringCellValue())){ num ++; break; }else if(sheet.getRow(0).getPhysicalNumberOfCells() - 1 == j && num == 0){ flag = true; // true結束 break; } } // 根據模板表頭長度,讀取一行資料 for (int j = 0; j < sheet.getRow(0).getPhysicalNumberOfCells(); j++) { if(flag){ break; } // 屬於零件主資料匯入的判斷邏輯, sheet主資料 且下標是這個集合內的,判斷空則丟擲空異常 if ( sheetIndex.equals(0) && this.validateColumnIndexListForMainData.contains(j) && null == row.getCell(j) ) { map.put("5002", "匯入的Excel資料(Sheet1配件主資料)必填欄位存在空值!!!"); throw new ServiceBizException(ERR_MESSAGE); } else if (sheetIndex.equals(1) && null == row.getCell(j)) { map.put("5003", "匯入的Excel資料(Sheet2專屬價格)存在空值!!!"); throw new ServiceBizException(ERR_MESSAGE); } else if (sheetIndex.equals(2) && null == row.getCell(j)) { map.put("5004", "匯入的Excel資料(Sheet3替換件)存在空值!!!"); throw new ServiceBizException(ERR_MESSAGE); } if (row.getCell(j) == null) { dataMap.put(j, ""); } else { String parseExcel = parseExcel(row.getCell(j)).trim(); if (!StringUtils.isBlank(parseExcel)) { dataMap.put(j, parseExcel); isValidRow = true; } else { dataMap.put(j, ""); } } } /** * 讀取完一條記錄,如果是有效資料行,則加入返回結果中 */ if (isValidRow) { dataList.add(dataMap); } } } if (CollectionUtils.isEmpty(dataList) && sheetIndex.equals(0)) { map.put("5001", "匯入的Excel資料不能為空"); throw new ServiceBizException(ERR_MESSAGE); } return dataList; }
這裡有一段解析處理,有點麻煩
private static String parseExcel(Cell cell) { String result = ""; switch (cell.getCellType()) { case HSSFCell.CELL_TYPE_NUMERIC:// 數字型別 if (HSSFDateUtil.isCellDateFormatted(cell)) {// 處理日期格式、時間格式 SimpleDateFormat sdf = null; if (cell.getCellStyle().getDataFormat() == HSSFDataFormat.getBuiltinFormat("h:mm")) { sdf = new SimpleDateFormat("HH:mm"); } else {// 日期 sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); } Date date = cell.getDateCellValue(); result = sdf.format(date); } else if (cell.getCellStyle().getDataFormat() == 58) { // 處理自定義日期格式:m月d日(通過判斷單元格的格式id解決,id的值是58) SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); double value = cell.getNumericCellValue(); Date date = org.apache.poi.ss.usermodel.DateUtil.getJavaDate(value); result = sdf.format(date); } else { cell.setCellType(XSSFCell.CELL_TYPE_STRING); result = cell.getStringCellValue().toString(); } break; case HSSFCell.CELL_TYPE_STRING:// String型別 result = cell.getRichStringCellValue().toString(); break; case HSSFCell.CELL_TYPE_BLANK: result = ""; break; default: result = ""; break; } return result;
然後第二部分資料封裝物件來插入DB:
/** * * @param datas * @return */ private Integer insertPartMainData(List<Map<Integer, String>> datas) throws Exception { Integer affectRows = 0; Class<PartInfoPO> partInfoPOClass = PartInfoPO.class; PartInfoPO partInfoPO ; // 先遍歷集合 for (Map<Integer, String> row : datas) { partInfoPO = new PartInfoPO(); partInfoPO.setOwnerCode("-1"); // pmd是每一行的結果 Set<Integer> columns = row.keySet(); // 遍歷每一行獲取單元格的值 for (Integer column : columns) { String fieldKey = fields.get(column); String fieldValue = row.get(column); if(StringUtils.isNullOrEmpty(fieldValue)){continue;} Field field = partInfoPOClass.getDeclaredField(fieldKey); field.setAccessible(true); Class<?> type = field.getType(); fieldValue = "是".equals(fieldValue) ? YES : "否".equals(fieldValue) ? NO : fieldValue; if (Integer.class.equals(type)) { // fieldValue = "是".equals(fieldValue) ? "10041001" : "否".equals(fieldValue) ? "10041002" : fieldValue; field.set(partInfoPO, Integer.valueOf(fieldValue)); } else if(BigDecimal.class.equals(type)) { // fieldValue = "是".equals(fieldValue) ? "10041001" : "否".equals(fieldValue) ? "10041002" : fieldValue; field.set(partInfoPO, new BigDecimal(fieldValue)); } else if(Date.class.equals(type) ) { SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy/MM/dd"); field.set(partInfoPO, simpleDateFormat.parse(fieldValue)); } else { field.set(partInfoPO, fieldValue); } } affectRows += partInfoMapper.insert(partInfoPO); } return affectRows; }