前端页面设置了列表表头 的动态查询,用户可以自己设置那些需要关注的字段,为此,后端需要保持导出的表头与前端一致。
本文介绍如何使用spring boot+easyExcel,动态导出数据。
步骤1.设置实体类
java
@Data
public class RepairWorkOrder extends BaseEntity {
//自增主键ID
private Integer id;
//工单号码
@TableField(condition = SqlCondition.LIKE)
private String orderNo;
//设备SN
@TableField(condition = SqlCondition.LIKE)
private String deviceSn;
//设备型号
@TableField(condition = SqlCondition.LIKE)
private String deviceModel;
//设备类型
private String deviceType;
//工单类型(0-售后工单、1-自制工单)
private Integer type;
}
步骤2.设置导出实体
java
@SuppressWarnings("serial")
@Data
@ColumnWidth(20)
public class RepairWorkOrderExportDTO {
@ExcelProperty(value = "工单号")
private String orderNo;
//工单状态:0-待定性定责 1-待分配维修工程师 2-待维修测试 3-待交付 4-已完成
@ExcelProperty(value = "工单状态")
private String statusString;
private Integer status;
@ExcelProperty(value = "设备SN")
private String deviceSn;
//设备型号
@ExcelProperty(value = "设备型号")
private String deviceModel;
//工单类型(0-售后工单、1-自制产品维修)
@ExcelProperty(value = "工单类型")
private String typeString;
private Integer type;
}
步骤3.加依赖(EasyExcel Spring Boot Starter)
xml
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>easyexcel-spring-boot-starter</artifactId>
<version>3.3.2</version>
</dependency>
步骤4.动态导出工具方法
数据列表:dataList
导出表头列表:includeColumnFieldNames,这里使用LinkedHashSet,保证导出表头的顺序和传入的参数顺序一致。
响应:response
java
public void exportDynamicExcel(
List<RepairWorkOrderExportDTO> dataList,
LinkedHashSet<String> includeColumnFieldNames,
HttpServletResponse response) throws IOException {
if (ObjectUtil.isNull(dataList)) {
throw new ValidateException("导出参数不能为空");
}
if (ObjectUtil.isEmpty(includeColumnFieldNames)) {
throw new ValidateException("导出字段列表不能为空");
}
response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
response.setCharacterEncoding("utf-8");
String fileName = "维修工单列表_" + System.currentTimeMillis() + ".xlsx";
response.setHeader("Content-Disposition", "attachment; filename=\"" +
java.net.URLEncoder.encode(fileName, "UTF-8").replaceAll("\\+", "%20") + "\"");
try (OutputStream out = response.getOutputStream()) {
ExcelWriterBuilder writerBuilder = EasyExcel.write(out, RepairWorkOrderExportDTO.class)
.includeColumnFiledNames(includeColumnFieldNames)
.registerWriteHandler(new LongestMatchColumnWidthStyleStrategy())
.registerConverter(LocalDateStringConverter.INSTANCE) //Date日期转化工具,如无date类型可以去掉
.registerConverter(LocalDateTimeStringConverter.INSTANCE) //DateTime日期转化工具,如无dateTime类型可以去掉
;
writerBuilder.sheet("维修工单列表").doWrite(dataList);
} catch (Exception e) {
log.error("导出异常", e);
throw new ValidateException("导出异常");
}
}
步骤5.状态等字段翻译成文字
这里我就使用最简单的方法了,遍历然后翻译。
java
private void translateStatus(List<RepairWorkOrderExportDTO> list) {
if (list == null || list.isEmpty()) {
return;
}
for (RepairWorkOrderExportDTO dto : list) {
if (dto == null) {
continue;
}
dto.setTypeString(dto.getType() == 0 ? Constant.type0 : Constant.type1);
dto.setStatusString(STATUS_MAP.getOrDefault(dto.getStatus(), "未知状态"));
Integer warrantyStatus = dto.getWarrantyStatus();
String deviceType = dto.getDeviceType();
if (deviceType != null){
if (ServiceOrderEnum.UAV.getDescEN().equals(dto.getDeviceType())){
dto.setDeviceType(ServiceOrderEnum.UAV.getDesc());
}
if (ServiceOrderEnum.LOAD.getDescEN().equals(dto.getDeviceType())){
dto.setDeviceType(ServiceOrderEnum.LOAD.getDesc());
}
if (ServiceOrderEnum.NEST.getDescEN().equals(dto.getDeviceType())){
dto.setDeviceType(ServiceOrderEnum.NEST.getDesc());
}
}
}
}