package com.youchain.utils; import cn.idev.excel.ExcelWriter; import cn.idev.excel.FastExcel; import cn.idev.excel.write.metadata.WriteSheet; import cn.idev.excel.write.metadata.style.WriteCellStyle; import cn.idev.excel.write.metadata.style.WriteFont; import cn.idev.excel.write.style.HorizontalCellStyleStrategy; import com.youchain.exception.BadRequestException; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; import org.apache.poi.ss.usermodel.IndexedColors; import org.springframework.http.HttpHeaders; import org.springframework.http.MediaType; import org.springframework.http.MediaTypeFactory; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.io.UnsupportedEncodingException; import java.net.URLEncoder; import java.util.Collection; import java.util.List; import java.util.function.BiFunction; import java.util.function.Function; import java.util.function.ToLongFunction; import java.util.stream.Collectors; import static cn.hutool.core.util.CharsetUtil.UTF_8; /** * excel 工具类 */ @Slf4j public class FastExcelUtil { /** * 设置下载文件消息头 * * @param response 响应 * @param fileName 文件名 * @param fileSize 文件大小 */ public static void setDownloadFileHeader(HttpServletResponse response, String fileName, Long fileSize) { response.setCharacterEncoding(UTF_8); if (fileSize != null) { response.setHeader(HttpHeaders.CONTENT_LENGTH, String.valueOf(fileSize)); } if (StringUtils.isNotEmpty(fileName)) { response.setHeader(HttpHeaders.CONTENT_TYPE, MediaTypeFactory.getMediaType(fileName).orElse(MediaType.APPLICATION_OCTET_STREAM) + ";charset=utf-8"); try { response.setHeader(HttpHeaders.CONTENT_DISPOSITION, "attachment;filename=" + URLEncoder.encode(fileName, UTF_8).replaceAll("\\+", "%20")); } catch (UnsupportedEncodingException e) { throw new RuntimeException(e); } response.setHeader(HttpHeaders.ACCESS_CONTROL_EXPOSE_HEADERS, HttpHeaders.CONTENT_DISPOSITION); } } /** * 获取样式 * * @return horizontalCellStyleStrategy */ public static HorizontalCellStyleStrategy getHorizontalCellStyleStrategy() { WriteCellStyle headWriteCellStyle = new WriteCellStyle(); headWriteCellStyle.setFillForegroundColor(IndexedColors.SKY_BLUE.getIndex()); WriteFont headWriteFont = new WriteFont(); headWriteFont.setFontName("宋体"); headWriteFont.setColor(IndexedColors.WHITE.getIndex()); headWriteCellStyle.setWriteFont(headWriteFont); WriteCellStyle contentWriteCellStyle = new WriteCellStyle(); contentWriteCellStyle.setFillForegroundColor(IndexedColors.BLACK.getIndex()); return new HorizontalCellStyleStrategy(headWriteCellStyle, contentWriteCellStyle); } /** * 通用单sheet导出 */ public static void exportExcel(HttpServletResponse response, String fileName, String sheetName, Class head, Collection data) throws IOException { // 设置下载消息头 setDownloadFileHeader(response, fileName, null); //样式 HorizontalCellStyleStrategy horizontalCellStyleStrategy = getHorizontalCellStyleStrategy(); // 下载 FastExcel.write(response.getOutputStream(), head) .autoCloseStream(Boolean.FALSE) .sheet(sheetName) .registerWriteHandler(horizontalCellStyleStrategy) .doWrite(data); } /** * 大数据导出 * @param response 响应 * @param fileName 文件名 * @param sheetName sheet名称 * @param head 头 * @param pageQueryFunction 查询方法 * @param convertFunction 转换方法 * @param idExtractor id提取方法 * @param pageSize 每页大小 * @param 泛型 * @param 泛型 */ public static void batchExportExcel(HttpServletResponse response, String fileName, String sheetName, Class head, BiFunction> pageQueryFunction, Function convertFunction, ToLongFunction idExtractor, int pageSize) { long startTime = System.currentTimeMillis(); // 设置下载消息头 setDownloadFileHeader(response, fileName, null); HorizontalCellStyleStrategy horizontalCellStyleStrategy = getHorizontalCellStyleStrategy(); try (ExcelWriter excelWriter = FastExcel.write(response.getOutputStream(), head).registerWriteHandler(horizontalCellStyleStrategy).build()) { WriteSheet writeSheet = FastExcel.writerSheet(sheetName).build(); long lastId = 0;//最后一个id while (true) { List batch = pageQueryFunction.apply(lastId, pageSize); if (batch.isEmpty()) { break; } List excelData = batch.stream() .map(convertFunction) .collect(Collectors.toList()); excelWriter.write(excelData, writeSheet); lastId = batch.stream() .mapToLong(idExtractor) .max() .orElse(lastId); } excelWriter.finish(); log.info("导出总耗时: {}ms", System.currentTimeMillis() - startTime); } catch (Exception e) { throw new BadRequestException("导出失败"); } } }