导出评估申请表格
This commit is contained in:
@@ -6,6 +6,7 @@ import io.swagger.v3.oas.annotations.Operation;
|
|||||||
import io.swagger.v3.oas.annotations.Parameter;
|
import io.swagger.v3.oas.annotations.Parameter;
|
||||||
import io.swagger.v3.oas.annotations.media.Schema;
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||||
|
import jakarta.servlet.http.HttpServletResponse;
|
||||||
import jakarta.validation.Valid;
|
import jakarta.validation.Valid;
|
||||||
import jakarta.validation.constraints.NotBlank;
|
import jakarta.validation.constraints.NotBlank;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
@@ -107,4 +108,18 @@ public class LbAssessmentApplyController {
|
|||||||
return ResponseEntity.internalServerError().body(result);
|
return ResponseEntity.internalServerError().body(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@GetMapping("/export")
|
||||||
|
@Operation(summary = "导出申请评估Excel", description = "按租户ID与申请日期时间范围导出申请评估列表")
|
||||||
|
public void export(
|
||||||
|
@Parameter(description = "租户ID", required = true) @RequestParam String tenantId,
|
||||||
|
@Parameter(description = "申请开始时间,格式:yyyy-MM-dd HH:mm:ss", required = true)
|
||||||
|
@RequestParam String applicationDatetimeStart,
|
||||||
|
@Parameter(description = "申请结束时间,格式:yyyy-MM-dd HH:mm:ss", required = true)
|
||||||
|
@RequestParam String applicationDatetimeEnd,
|
||||||
|
HttpServletResponse response) {
|
||||||
|
lbAssessmentApplyService.exportExcel(
|
||||||
|
tenantId, applicationDatetimeStart, applicationDatetimeEnd, response
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ package com.rj.service;
|
|||||||
|
|
||||||
import com.baomidou.mybatisplus.extension.service.IService;
|
import com.baomidou.mybatisplus.extension.service.IService;
|
||||||
import com.rj.entity.LbAssessmentApply;
|
import com.rj.entity.LbAssessmentApply;
|
||||||
|
import jakarta.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
@@ -29,4 +30,9 @@ public interface ILbAssessmentApplyService extends IService<LbAssessmentApply> {
|
|||||||
*/
|
*/
|
||||||
Map<String, Object> parseFromAssessmentTextByLlm(String assessmentText, String tenantId);
|
Map<String, Object> parseFromAssessmentTextByLlm(String assessmentText, String tenantId);
|
||||||
|
|
||||||
|
void exportExcel(String tenantId,
|
||||||
|
String applicationDatetimeStart,
|
||||||
|
String applicationDatetimeEnd,
|
||||||
|
HttpServletResponse response);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,14 +14,26 @@ import com.fasterxml.jackson.databind.ObjectMapper;
|
|||||||
import com.rj.entity.LbAssessmentApply;
|
import com.rj.entity.LbAssessmentApply;
|
||||||
import com.rj.mapper.LbAssessmentApplyMapper;
|
import com.rj.mapper.LbAssessmentApplyMapper;
|
||||||
import com.rj.service.ILbAssessmentApplyService;
|
import com.rj.service.ILbAssessmentApplyService;
|
||||||
|
import jakarta.servlet.ServletOutputStream;
|
||||||
|
import jakarta.servlet.http.HttpServletResponse;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.apache.poi.ss.usermodel.*;
|
||||||
|
import org.apache.poi.xssf.usermodel.XSSFCellStyle;
|
||||||
|
import org.apache.poi.xssf.usermodel.XSSFColor;
|
||||||
|
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.beans.factory.annotation.Value;
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
|
import org.springframework.http.HttpHeaders;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import java.awt.Color;
|
||||||
|
import java.net.URLEncoder;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
|
import java.time.format.DateTimeFormatter;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
@@ -250,33 +262,10 @@ public class LbAssessmentApplyServiceImpl
|
|||||||
size = 10;
|
size = 10;
|
||||||
}
|
}
|
||||||
|
|
||||||
LambdaQueryWrapper<LbAssessmentApply> queryWrapper = new LambdaQueryWrapper<>();
|
LambdaQueryWrapper<LbAssessmentApply> queryWrapper = buildQueryWrapper(
|
||||||
if (tenantId != null && !tenantId.trim().isEmpty()) {
|
tenantId, applicantName, applicantPhone, colleagueName, teamLeaderName,
|
||||||
queryWrapper.eq(LbAssessmentApply::getTenantId, tenantId.trim());
|
assessmentTeacherName, moderatorName, meetingNumber
|
||||||
}
|
);
|
||||||
if (applicantName != null && !applicantName.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getApplicantName, applicantName.trim());
|
|
||||||
}
|
|
||||||
if (applicantPhone != null && !applicantPhone.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getApplicantPhone, applicantPhone.trim());
|
|
||||||
}
|
|
||||||
if (colleagueName != null && !colleagueName.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getColleagueName, colleagueName.trim());
|
|
||||||
}
|
|
||||||
if (teamLeaderName != null && !teamLeaderName.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getTeamLeaderName, teamLeaderName.trim());
|
|
||||||
}
|
|
||||||
if (assessmentTeacherName != null && !assessmentTeacherName.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getAssessmentTeacherName, assessmentTeacherName.trim());
|
|
||||||
}
|
|
||||||
if (moderatorName != null && !moderatorName.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getModeratorName, moderatorName.trim());
|
|
||||||
}
|
|
||||||
if (meetingNumber != null && !meetingNumber.trim().isEmpty()) {
|
|
||||||
queryWrapper.like(LbAssessmentApply::getMeetingNumber, meetingNumber.trim());
|
|
||||||
}
|
|
||||||
queryWrapper.orderByDesc(LbAssessmentApply::getUpdatedAt)
|
|
||||||
.orderByDesc(LbAssessmentApply::getCreatedAt);
|
|
||||||
|
|
||||||
Page<LbAssessmentApply> page = this.page(new Page<>(current, size), queryWrapper);
|
Page<LbAssessmentApply> page = this.page(new Page<>(current, size), queryWrapper);
|
||||||
result.put("success", true);
|
result.put("success", true);
|
||||||
@@ -294,4 +283,193 @@ public class LbAssessmentApplyServiceImpl
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void exportExcel(String tenantId,
|
||||||
|
String applicationDatetimeStart,
|
||||||
|
String applicationDatetimeEnd,
|
||||||
|
HttpServletResponse response) {
|
||||||
|
try {
|
||||||
|
if (tenantId == null || tenantId.trim().isEmpty()) {
|
||||||
|
response.sendError(HttpServletResponse.SC_BAD_REQUEST, "tenantId不能为空");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (applicationDatetimeStart == null || applicationDatetimeStart.trim().isEmpty()) {
|
||||||
|
response.sendError(HttpServletResponse.SC_BAD_REQUEST, "applicationDatetimeStart不能为空");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (applicationDatetimeEnd == null || applicationDatetimeEnd.trim().isEmpty()) {
|
||||||
|
response.sendError(HttpServletResponse.SC_BAD_REQUEST, "applicationDatetimeEnd不能为空");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
|
||||||
|
LocalDateTime start;
|
||||||
|
LocalDateTime end;
|
||||||
|
try {
|
||||||
|
start = LocalDateTime.parse(applicationDatetimeStart.trim(), formatter);
|
||||||
|
} catch (Exception e) {
|
||||||
|
response.sendError(HttpServletResponse.SC_BAD_REQUEST, "申请开始时间格式错误,请使用 yyyy-MM-dd HH:mm:ss");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
end = LocalDateTime.parse(applicationDatetimeEnd.trim(), formatter);
|
||||||
|
} catch (Exception e) {
|
||||||
|
response.sendError(HttpServletResponse.SC_BAD_REQUEST, "申请结束时间格式错误,请使用 yyyy-MM-dd HH:mm:ss");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (start.isAfter(end)) {
|
||||||
|
response.sendError(HttpServletResponse.SC_BAD_REQUEST, "申请开始时间不能晚于结束时间");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
LambdaQueryWrapper<LbAssessmentApply> queryWrapper = new LambdaQueryWrapper<>();
|
||||||
|
queryWrapper.eq(LbAssessmentApply::getTenantId, tenantId.trim())
|
||||||
|
.ge(LbAssessmentApply::getApplicationDatetime, start)
|
||||||
|
.le(LbAssessmentApply::getApplicationDatetime, end)
|
||||||
|
.orderByDesc(LbAssessmentApply::getApplicationDatetime);
|
||||||
|
List<LbAssessmentApply> rows = this.list(queryWrapper);
|
||||||
|
|
||||||
|
try (Workbook workbook = new XSSFWorkbook()) {
|
||||||
|
Sheet sheet = workbook.createSheet("申请评估");
|
||||||
|
|
||||||
|
CellStyle headerStyle = workbook.createCellStyle();
|
||||||
|
Font headerFont = workbook.createFont();
|
||||||
|
headerFont.setBold(true);
|
||||||
|
headerStyle.setFont(headerFont);
|
||||||
|
headerStyle.setAlignment(HorizontalAlignment.CENTER);
|
||||||
|
headerStyle.setVerticalAlignment(VerticalAlignment.CENTER);
|
||||||
|
headerStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND);
|
||||||
|
((XSSFCellStyle) headerStyle).setFillForegroundColor(new XSSFColor(new Color(255, 217, 102), null));
|
||||||
|
headerStyle.setBorderTop(BorderStyle.THIN);
|
||||||
|
headerStyle.setBorderBottom(BorderStyle.THIN);
|
||||||
|
headerStyle.setBorderLeft(BorderStyle.THIN);
|
||||||
|
headerStyle.setBorderRight(BorderStyle.THIN);
|
||||||
|
|
||||||
|
CellStyle dataStyle = workbook.createCellStyle();
|
||||||
|
dataStyle.setAlignment(HorizontalAlignment.CENTER);
|
||||||
|
dataStyle.setVerticalAlignment(VerticalAlignment.CENTER);
|
||||||
|
dataStyle.setBorderTop(BorderStyle.THIN);
|
||||||
|
dataStyle.setBorderBottom(BorderStyle.THIN);
|
||||||
|
dataStyle.setBorderLeft(BorderStyle.THIN);
|
||||||
|
dataStyle.setBorderRight(BorderStyle.THIN);
|
||||||
|
|
||||||
|
String[] headers = {
|
||||||
|
"序号", "申请人", "电话", "同事", "电话", "团队长", "全收益团队长",
|
||||||
|
"整理确定时间", "安排评估老师", "安排主持人", "会议号"
|
||||||
|
};
|
||||||
|
|
||||||
|
Row headerRow = sheet.createRow(0);
|
||||||
|
headerRow.setHeightInPoints(22);
|
||||||
|
for (int i = 0; i < headers.length; i++) {
|
||||||
|
createCell(headerRow, i, headers[i], headerStyle);
|
||||||
|
}
|
||||||
|
|
||||||
|
int rowIndex = 1;
|
||||||
|
for (LbAssessmentApply item : rows) {
|
||||||
|
Row row = sheet.createRow(rowIndex);
|
||||||
|
row.setHeightInPoints(20);
|
||||||
|
createCell(row, 0, String.valueOf(rowIndex), dataStyle);
|
||||||
|
createCell(row, 1, nullToEmpty(item.getApplicantName()), dataStyle);
|
||||||
|
createCell(row, 2, nullToEmpty(item.getApplicantPhone()), dataStyle);
|
||||||
|
createCell(row, 3, nullToEmpty(item.getColleagueName()), dataStyle);
|
||||||
|
createCell(row, 4, nullToEmpty(item.getColleaguePhone()), dataStyle);
|
||||||
|
createCell(row, 5, nullToEmpty(item.getTeamLeaderName()), dataStyle);
|
||||||
|
createCell(row, 6, "", dataStyle);
|
||||||
|
createCell(row, 7, formatApplicationDatetime(item.getApplicationDatetime()), dataStyle);
|
||||||
|
createCell(row, 8, nullToEmpty(item.getAssessmentTeacherName()), dataStyle);
|
||||||
|
createCell(row, 9, nullToEmpty(item.getModeratorName()), dataStyle);
|
||||||
|
createCell(row, 10, nullToEmpty(item.getMeetingNumber()), dataStyle);
|
||||||
|
rowIndex++;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < headers.length; i++) {
|
||||||
|
sheet.autoSizeColumn(i);
|
||||||
|
int width = sheet.getColumnWidth(i);
|
||||||
|
sheet.setColumnWidth(i, Math.min(255 * 256, (int) (width * 1.2)));
|
||||||
|
}
|
||||||
|
|
||||||
|
String filename = "申请评估_" + LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyyMMddHHmmss")) + ".xlsx";
|
||||||
|
String encoded = URLEncoder.encode(filename, StandardCharsets.UTF_8).replaceAll("\\+", "%20");
|
||||||
|
|
||||||
|
response.setCharacterEncoding(StandardCharsets.UTF_8.name());
|
||||||
|
response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
|
||||||
|
response.setHeader(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename*=UTF-8''" + encoded);
|
||||||
|
|
||||||
|
try (ServletOutputStream os = response.getOutputStream()) {
|
||||||
|
workbook.write(os);
|
||||||
|
os.flush();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("申请评估导出异常", e);
|
||||||
|
try {
|
||||||
|
response.reset();
|
||||||
|
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
|
||||||
|
response.setCharacterEncoding(StandardCharsets.UTF_8.name());
|
||||||
|
response.setContentType("text/plain;charset=UTF-8");
|
||||||
|
response.getWriter().write("导出异常:" + e.getMessage());
|
||||||
|
} catch (Exception ignored) {
|
||||||
|
// ignore
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private LambdaQueryWrapper<LbAssessmentApply> buildQueryWrapper(String tenantId,
|
||||||
|
String applicantName,
|
||||||
|
String applicantPhone,
|
||||||
|
String colleagueName,
|
||||||
|
String teamLeaderName,
|
||||||
|
String assessmentTeacherName,
|
||||||
|
String moderatorName,
|
||||||
|
String meetingNumber) {
|
||||||
|
LambdaQueryWrapper<LbAssessmentApply> queryWrapper = new LambdaQueryWrapper<>();
|
||||||
|
if (tenantId != null && !tenantId.trim().isEmpty()) {
|
||||||
|
queryWrapper.eq(LbAssessmentApply::getTenantId, tenantId.trim());
|
||||||
|
}
|
||||||
|
if (applicantName != null && !applicantName.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getApplicantName, applicantName.trim());
|
||||||
|
}
|
||||||
|
if (applicantPhone != null && !applicantPhone.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getApplicantPhone, applicantPhone.trim());
|
||||||
|
}
|
||||||
|
if (colleagueName != null && !colleagueName.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getColleagueName, colleagueName.trim());
|
||||||
|
}
|
||||||
|
if (teamLeaderName != null && !teamLeaderName.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getTeamLeaderName, teamLeaderName.trim());
|
||||||
|
}
|
||||||
|
if (assessmentTeacherName != null && !assessmentTeacherName.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getAssessmentTeacherName, assessmentTeacherName.trim());
|
||||||
|
}
|
||||||
|
if (moderatorName != null && !moderatorName.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getModeratorName, moderatorName.trim());
|
||||||
|
}
|
||||||
|
if (meetingNumber != null && !meetingNumber.trim().isEmpty()) {
|
||||||
|
queryWrapper.like(LbAssessmentApply::getMeetingNumber, meetingNumber.trim());
|
||||||
|
}
|
||||||
|
queryWrapper.orderByDesc(LbAssessmentApply::getUpdatedAt)
|
||||||
|
.orderByDesc(LbAssessmentApply::getCreatedAt);
|
||||||
|
return queryWrapper;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String nullToEmpty(String value) {
|
||||||
|
return value == null ? "" : value;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String formatApplicationDatetime(LocalDateTime datetime) {
|
||||||
|
if (datetime == null) {
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
if (datetime.getMinute() == 0 && datetime.getSecond() == 0) {
|
||||||
|
return datetime.getMonthValue() + "." + datetime.getDayOfMonth() + "日" + datetime.getHour() + "点";
|
||||||
|
}
|
||||||
|
return datetime.format(DateTimeFormatter.ofPattern("M月d日 H:mm"));
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void createCell(Row row, int col, String text, CellStyle style) {
|
||||||
|
Cell cell = row.createCell(col);
|
||||||
|
cell.setCellValue(text);
|
||||||
|
cell.setCellStyle(style);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user