| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683 |
- package com.hotent.project.service;
- import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
- import com.hotent.base.util.StringUtil;
- import com.hotent.baseInfo.manager.AuditedUnitManager;
- import com.hotent.config.EipConfig;
- import com.hotent.project.manager.*;
- import com.hotent.project.model.*;
- import com.hotent.surveyinfo.manager.CostSurveyTemplateUploadManager;
- import com.hotent.surveyinfo.model.CostSurveyTemplateUpload;
- import com.hotent.uc.manager.OrgManager;
- import com.hotent.uc.manager.UserManager;
- import com.hotent.uc.model.Org;
- import com.hotent.uc.model.User;
- import com.hotent.uc.util.ContextUtil;
- import com.hotent.util.FileUploadUtil;
- import com.hotent.util.wordexcelutils.CompleteTemplateProcessor;
- import com.hotent.util.wordexcelutils.SmartTemplateWriter;
- import org.apache.pdfbox.pdmodel.PDDocument;
- import org.apache.poi.xwpf.usermodel.*;
- import org.slf4j.Logger;
- import org.slf4j.LoggerFactory;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.scheduling.annotation.Async;
- import org.springframework.stereotype.Service;
- import java.io.FileOutputStream;
- import java.time.LocalDateTime;
- import java.util.Comparator;
- import java.util.List;
- import java.util.Map;
- import java.util.stream.Collectors;
- /**
- * 异步资料归纳服务
- *
- * @company 山西清众科技股份有限公司
- * @author 超级管理员
- * @since 2025-12-02
- */
- @Service
- public class AsyncMaterialSummaryService {
- private static final Logger logger = LoggerFactory.getLogger(AsyncMaterialSummaryService.class);
- @Autowired
- private CostProjectTaskMaterialSummaryManager costProjectTaskMaterialSummaryManager;
- @Autowired
- private CostProjectTaskMaterialSummaryDetailManager costProjectTaskMaterialSummaryDetailManager;
- @Autowired
- private CostProjectDocumentManager costProjectDocumentManager;
- @Autowired
- private CostProjectTaskManager costProjectTaskManager;
- @Autowired
- private CostSurveyTemplateUploadManager costSurveyTemplateUploadManager;
- @Autowired
- private CostProjectTaskMaterialManager costProjectTaskMaterialManager;
- @Autowired
- private CostProjectDeliberateManager costProjectDeliberateManager;
- @Autowired
- private CostProjectTaskAdjustmentRecordManager adjustmentRecordManager;
- @Autowired
- private CostProjectTaskEvidenceManager costProjectTaskEvidenceManager;
- @Autowired
- private CostProjectTaskPreliminaryOpinionManager preliminaryOpinionManager;
- @Autowired
- private CostProjectApprovalManager costProjectApprovalManager;
- @Autowired
- private AuditedUnitManager auditedUnitManager;
- @Autowired
- private OrgManager orgManager;
- @Autowired
- private UserManager userManager;
- // 从配置文件读取模板路径
- @org.springframework.beans.factory.annotation.Value("${archive.template.coverPath:}")
- private String coverTemplatePath;
- @org.springframework.beans.factory.annotation.Value("${archive.template.catalogPath:}")
- private String catalogTemplatePath;
- @org.springframework.beans.factory.annotation.Value("${archive.template.backCoverPath:}")
- private String backCoverTemplatePath;
- /**
- * 生成资料归纳主表(14个基础资料类别)- 核心逻辑
- *
- * @param mainTask 主任务
- * @param childTasks 子任务列表
- */
- public void generateMaterialSummary(CostProjectTask mainTask, List<CostProjectTask> childTasks) {
- try {
- // 定义14个基础资料类别
- String[] materialNames = {
- "成本监审报告(含成本监审报告签发稿、送达回证)",
- "被监审单位申请定(调)价报告(复印件)",
- "成本监审通知书(含送达回证)",
- "经营者需提供成本资料清单",
- "《政府定价成本监审调查表》",
- "成本监审补充资料通知书(含送达回证)",
- "成本审核初步意见告知书(含送达回证)",
- "经营者书面反馈的材料",
- "成本审核初步意见表(集体审议用)",
- "成本监审集体审议记录",
- "成本监审工作底稿",
- "成本监审提取资料登记表",
- "提取的成本资料和会计凭证等复印件",
- "中止定价成本监审料通知书(含送达回证)"
- };
- // 为主任务生成14个资料归纳主表记录
- for (int i = 0; i < materialNames.length; i++) {
- CostProjectTaskMaterialSummary summary = new CostProjectTaskMaterialSummary();
- summary.setTaskId(mainTask.getId());
- summary.setMaterialName(materialNames[i]);
- summary.setMaterialOrderNum(i + 1);
- summary.setIsDeleted("0");
- costProjectTaskMaterialSummaryManager.createOrUpdate(summary);
- // 根据不同的资料类别生成对应的明细记录
- generateDetailsByMaterialType(summary, mainTask, childTasks, i + 1);
- }
- } catch (Exception e) {
- // 记录异常日志,但不影响主流程
- logger.error("生成资料归纳失败", e);
- }
- }
- /**
- * 根据资料类别生成对应的明细记录
- *
- * @param summary 资料归纳主表
- * @param mainTask 主任务
- * @param childTasks 子任务列表
- * @param materialType 资料类别序号(1-13)
- */
- private void generateDetailsByMaterialType(CostProjectTaskMaterialSummary summary,
- CostProjectTask mainTask,
- List<CostProjectTask> childTasks,
- int materialType) {
- try {
- // 查询项目下的所有文书
- List<CostProjectDocument> documents = costProjectDocumentManager.getListByProjectId(mainTask.getProjectId());
- if (documents == null) {
- documents = new java.util.ArrayList<>();
- }
- switch (materialType) {
- case 1:
- // 成本监审报告(含成本监审报告签发稿、送达回证)
- generateType1Details(summary, mainTask, documents);
- break;
- case 2:
- // 被监审单位申请定(调)价报告(复印件)
- generateType2Details(summary, mainTask, childTasks, documents);
- break;
- case 3:
- // 成本监审通知书(含送达回证)
- generateType3Details(summary, mainTask, childTasks, documents);
- break;
- case 4:
- // 经营者需提供成本资料清单
- generateType4Details(summary, mainTask, childTasks, documents);
- break;
- case 5:
- // 《政府定价成本监审调查表》
- generateType5Details(summary, mainTask, childTasks, documents);
- break;
- case 6:
- // 成本监审补充资料通知书(含送达回证)
- generateType6Details(summary, mainTask, childTasks, documents);
- break;
- case 7:
- // 成本审核初步意见告知书(含送达回证)
- generateType7Details(summary, mainTask, childTasks, documents);
- break;
- case 8:
- // 经营者书面反馈的材料
- generateType8Details(summary, mainTask, childTasks, documents);
- break;
- case 9:
- // 成本审核初步意见表(集体审议用)
- generateType9Details(summary, mainTask, childTasks, documents);
- break;
- case 10:
- // 成本监审集体审议记录
- generateType10Details(summary, mainTask, documents);
- break;
- case 11:
- // 成本监审工作底稿
- generateType11Details(summary, mainTask, childTasks, documents);
- break;
- case 12:
- // 成本监审提取资料登记表
- generateType12Details(summary, mainTask, childTasks, documents);
- break;
- case 13:
- // 提取的成本资料和会计凭证等复印件
- generateType13Details(summary, mainTask, childTasks, documents);
- break;
- case 14:
- // 中止定价成本监审料通知书(含送达回证)
- generateType14Details(summary, mainTask, childTasks, documents);
- break;
- default:
- throw new RuntimeException("未知的资料类型");
- }
- } catch (Exception e) {
- logger.error("生成资料类型 {} 的明细时出错:{}", materialType, e.getMessage(), e);
- // 继续执行,不中断整个流程
- }
- }
- //1 卷宗封面
- //2 卷内目录
- //3 政府定价成本监审结论报告
- //4 成本监审通知书
- //5 成本审核初步意见告知书
- //6 成本审核初步意见表
- //7 成本监审集体审议记录
- //8 成本监审工作底稿
- //9 成本监审提取资料登记表
- //10 成本监审补充资料通知书
- //11 中止定价成本监审通知书
- //12 送达回证
- //13 成本监审卷宗备考表
- // ==================== 类型1:成本监审报告(含成本监审报告签发稿、送达回证) ====================
- // A.成本监审报告(含成本监审报告签发稿)
- // 包括成本监审报告、报告签发稿等文书。
- private void generateType1Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本监审报告"、"成本监审报告签发稿"、"送达回证"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "3".equals(doc.getDocumentType())
- || "3-12".equals(doc.getDocumentType() + "-" + doc.getDocumentTypeName())
- )
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- // ==================== 类型2:被监审单位申请定(调)价报告(复印件) ====================
- // 被监审单位申请定(调)价报告等。
- //来源:从“监审立项”附件获取。
- private void generateType2Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"申请定(调)价报告"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "申请定(调)价报告".equals(doc.getDocumentName()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getScanDocumentUrl() != null ? document.getScanDocumentUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- CostProjectApproval approval = costProjectApprovalManager.getById(mainTask.getProjectId());
- if (approval != null && StringUtil.isNotEmpty(approval.getAccordingFileUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName("成本项目定(调)价依据");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(mainTask.getAuditedUnitId());
- detail.setAuditedUnitName(mainTask.getAuditedUnitName() != null ? mainTask.getAuditedUnitName() : "");
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(approval.getAccordingFileUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- // ==================== 类型3:成本监审通知书(含送达回证) ====================
- // 包括成本监审通知书、送达回证等文书。
- //来源:从“监审文书”中获取。
- private void generateType3Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // "成本监审通知书"和"送达回证"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "4".equals(doc.getDocumentType())
- || "4-12".equals(doc.getDocumentType() + "-" + doc.getDocumentTypeName()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- // ==================== 类型4:经营者需提供成本资料清单(提取资料) ====================
- // 成本监审任务中的资料报送要求。
- //来源:从“监审任务部署”中获取。
- private void generateType4Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本资料清单"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "9".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- for (CostProjectTask childTask : childTasks) {
- List<CostProjectTaskEvidence> list = costProjectTaskEvidenceManager.list(
- new LambdaQueryWrapper<CostProjectTaskEvidence>().eq(CostProjectTaskEvidence::getTaskId, childTask.getId())
- );
- for (CostProjectTaskEvidence evidence : list) {
- // 只处理有附件的资料登记
- if (StringUtil.isNotEmpty(evidence.getAttachmentUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(evidence.getMaterialName() != null ? evidence.getMaterialName() : "提取资料登记");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(childTask.getAuditedUnitId());
- detail.setAuditedUnitName(childTask.getAuditedUnitName() != null ? childTask.getAuditedUnitName() : "");
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(evidence.getPageCount() != null ? evidence.getPageCount() : 0);
- detail.setAttachmentUrl(evidence.getAttachmentUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- }
- // ==================== 类型5:《政府定价成本监审调查表》 ====================
- // 各被监审单位的“成本监审调查表”文档。
- //来源:从“监审任务”中获取各被监审单位填报的成本监审调查表。
- private void generateType5Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- for (CostProjectTask childTask : childTasks) {
- List<CostSurveyTemplateUpload> costSurveyTemplateUploads = costSurveyTemplateUploadManager.listByTaskId(childTask.getId());
- for (CostSurveyTemplateUpload upload : costSurveyTemplateUploads) {
- if ("1".equals(upload.getIsUpload()) && StringUtil.isNotEmpty(upload.getFileUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(upload.getSurveyTemplateName() != null ? upload.getSurveyTemplateName() : "政府定价成本监审调查表");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(childTask.getAuditedUnitId());
- detail.setAuditedUnitName(childTask.getAuditedUnitName() != null ? childTask.getAuditedUnitName() : "");
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(0);
- detail.setAttachmentUrl(upload.getFileUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- // 成本调查表(kkkk)
- }
- // ==================== 类型6:成本监审补充资料通知书(含送达回证) ====================
- // 监审主体发送给各被监审单位的补充资料通知书、送达回证等文书。
- //来源:从“监审文书”中获取。
- private void generateType6Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "10".equals(doc.getDocumentType())
- || "10-12".equals(doc.getDocumentType() + "-" + doc.getDocumentTypeName()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- // ==================== 类型7:成本审核初步意见告知书(含送达回证) ====================
- // 监审主体发送给各被监审单位的初步意见告知书、送达回证等文书。
- // 来源:从“监审文书”中获取。
- private void generateType7Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本审核初步意见告知书"和"送达回证"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "5".equals(doc.getDocumentType())
- || "5-12".equals(doc.getDocumentType() + "-" + doc.getDocumentTypeName()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- // ==================== 类型8:经营者书面反馈的材料 ====================
- // 各被监审单位对初步意见告知书的意见反馈资料。
- //来源:从“监审任务”中获取反馈意见。
- private void generateType8Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"书面反馈材料"(来源:监审单位反馈文件)
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "书面反馈材料".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- // 获取被监审单位的反馈意见和反馈资料
- for (CostProjectTask childTask : childTasks) {
- List<CostProjectTaskPreliminaryOpinion> list = preliminaryOpinionManager.list(
- new LambdaQueryWrapper<>(CostProjectTaskPreliminaryOpinion.class)
- .eq(CostProjectTaskPreliminaryOpinion::getTaskId, childTask.getId())
- );
- for (CostProjectTaskPreliminaryOpinion opinion : list) {
- // 只处理有反馈资料的记录
- if (StringUtil.isNotEmpty(opinion.getFeedbackMaterials())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName("书面反馈材料");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(childTask.getAuditedUnitId());
- detail.setAuditedUnitName(childTask.getAuditedUnitName() != null ? childTask.getAuditedUnitName() : "");
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(0);
- detail.setAttachmentUrl(opinion.getFeedbackMaterials());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- }
- // ==================== 类型9:成本审核初步意见表(集体审议用) ====================
- // 来源:从“监审文书”中获取
- private void generateType9Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本审核初步意见表"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "6".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- // ==================== 类型10:成本监审集体审议记录 ====================
- // 来源:从“监审文书”中获取。
- private void generateType10Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本监审集体审议记录"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "7".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- // 获取集体审议记录
- List<CostProjectDeliberate> list = costProjectDeliberateManager.list(
- new LambdaQueryWrapper<CostProjectDeliberate>().eq(CostProjectDeliberate::getTaskId, mainTask.getId())
- );
- for (CostProjectDeliberate deliberate : list) {
- // 只处理有附件的审议记录
- if (StringUtil.isNotEmpty(deliberate.getAttachmentUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName("成本监审集体审议记录");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(mainTask.getAuditedUnitId());
- detail.setAuditedUnitName(mainTask.getAuditedUnitName() != null ? mainTask.getAuditedUnitName() : "");
- detail.setFileSource("监审主体上传文件");
- detail.setPageCount(0);
- detail.setAttachmentUrl(deliberate.getAttachmentUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- // ==================== 类型11:成本监审工作底稿 ====================
- // 来源:从“监审文书”中获取。
- private void generateType11Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本监审工作底稿"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "8".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- // 获取核增核减记录(工作底稿的一部分)
- for (CostProjectTask childTask : childTasks) {
- List<CostProjectTaskAdjustmentRecord> costProjectTaskAdjustmentRecords = adjustmentRecordManager.listByTaskId(childTask.getId());
- for (CostProjectTaskAdjustmentRecord record : costProjectTaskAdjustmentRecords) {
- // 只处理有附件的记录
- if (StringUtil.isNotEmpty(record.getAttachmentUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(record.getSubject() != null ? record.getSubject() + "-工作底稿" : "成本监审工作底稿");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(childTask.getAuditedUnitId());
- detail.setAuditedUnitName(childTask.getAuditedUnitName() != null ? childTask.getAuditedUnitName() : "");
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(0);
- detail.setAttachmentUrl(record.getAttachmentUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- }
- // ==================== 类型12:成本监审提取资料登记表 ====================
- // 来源:从“监审文书”中获取。
- private void generateType12Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本监审提取资料登记表"
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "9".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- // 获取子任务的资料登记表
- for (CostProjectTask childTask : childTasks) {
- List<CostProjectTaskEvidence> list = costProjectTaskEvidenceManager.list(
- new LambdaQueryWrapper<CostProjectTaskEvidence>().eq(CostProjectTaskEvidence::getTaskId, childTask.getId())
- );
- for (CostProjectTaskEvidence evidence : list) {
- // 只处理有附件的资料登记
- if (StringUtil.isNotEmpty(evidence.getAttachmentUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(evidence.getMaterialName() != null ? evidence.getMaterialName() : "提取资料登记");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(childTask.getAuditedUnitId());
- detail.setAuditedUnitName(childTask.getAuditedUnitName() != null ? childTask.getAuditedUnitName() : "");
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(evidence.getPageCount() != null ? evidence.getPageCount() : 0);
- detail.setAttachmentUrl(evidence.getAttachmentUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- }
- // ==================== 类型13:提取的成本资料和会计凭证等复印件 ====================
- // 来源:各被监审单位首次及补充材料时提交的资料,包括综合性材料、财会资料等。
- private void generateType13Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"成本资料和会计凭证"(来源:被监审单位提交的资料)
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "成本资料和会计凭证".equals(doc.getDocumentType()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- // 获取子任务的资料登记表
- for (CostProjectTask childTask : childTasks) {
- // 获取任务的报送资料要求(被监审单位提交的补充资料)
- List<CostProjectTaskMaterial> list = costProjectTaskMaterialManager.list(
- new LambdaQueryWrapper<>(CostProjectTaskMaterial.class)
- .eq(CostProjectTaskMaterial::getTaskId, childTask.getId())
- );
- for (CostProjectTaskMaterial material : list) {
- // 只处理已上传的资料
- if ("1".equals(material.getIsUpload()) && StringUtil.isNotEmpty(material.getFileUrl())) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(material.getInformationName() != null ? material.getInformationName() : "补充资料");
- detail.setDocumentNumber("");
- detail.setAuditedUnitId(childTask.getAuditedUnitId());
- detail.setAuditedUnitName(childTask.getAuditedUnitName() != null ? childTask.getAuditedUnitName() : "");
- detail.setFileSource("监审单位反馈文件");
- detail.setPageCount(0);
- detail.setAttachmentUrl(material.getFileUrl());
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- }
- }
- // ==================== 类型14:中止定价成本监审料通知书(含送达回证) ====================
- // 来源:从“监审文书”中获取。
- private void generateType14Details(CostProjectTaskMaterialSummary summary, CostProjectTask mainTask, List<CostProjectTask> childTasks, List<CostProjectDocument> documents) {
- int orderNum = 1;
- // 获取"中止定价成本监审通知书"(来源:被监审单位提交的资料)
- List<CostProjectDocument> matchedDocuments = documents.stream()
- .filter(doc -> "11".equals(doc.getDocumentType())
- || "11-12".equals(doc.getDocumentType() + "-" + doc.getDocumentTypeName()))
- .sorted(Comparator.comparing(doc -> doc.getOrderNum() != null ? doc.getOrderNum() : 0))
- .collect(Collectors.toList());
- for (CostProjectDocument document : matchedDocuments) {
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(summary.getId());
- detail.setTaskId(mainTask.getId());
- detail.setDocumentName(document.getDocumentName());
- detail.setDocumentNumber(document.getDocumentNumber() != null ? document.getDocumentNumber() : "");
- detail.setAuditedUnitId(document.getEnterpriseId());
- if (document.getEnterpriseId() != null) {
- detail.setAuditedUnitName(auditedUnitManager.getById(document.getEnterpriseId()).getUnitName());
- }
- detail.setFileSource("系统生成电子文书");
- detail.setPageCount(0);
- detail.setAttachmentUrl(document.getActUrl() != null ? document.getActUrl() : "");
- detail.setOrderNum(orderNum++);
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- }
- /**
- * 档案校对通过后,异步生成Word卷宗
- * 顺序:封面(-1) -> 目录(-2) -> 14个资料(1-13) -> 封底(-3)
- *
- * @param taskId 任务ID
- */
- @Async
- public void generateWordArchiveAsync(String taskId) {
- CostProjectTask task = costProjectTaskManager.getById(taskId);
- try {
- logger.info("开始生成Word卷宗,任务ID:{}", taskId);
- // 查询任务的所有资料归纳主表(包含封面、目录、封底)
- List<CostProjectTaskMaterialSummary> allSummaryList =
- costProjectTaskMaterialSummaryManager.listAllByTaskId(taskId);
- // 创建Word文档
- XWPFDocument document = new XWPFDocument();
- boolean isFirstDocument = true;
- // 按顺序合并:封面(-1) -> 目录(-2) -> 14个资料(1-13) -> 封底(-3)
- // 排序:-1, -2, 1, 2, ..., 13, -3
- allSummaryList.sort((a, b) -> {
- int orderA = a.getMaterialOrderNum() != null ? a.getMaterialOrderNum() : 0;
- int orderB = b.getMaterialOrderNum() != null ? b.getMaterialOrderNum() : 0;
- // -1(封面) < -2(目录) < 1-13(资料) < -3(封底)
- int sortA = orderA == -1 ? -100 : (orderA == -2 ? -99 : (orderA == -3 ? 100 : orderA));
- int sortB = orderB == -1 ? -100 : (orderB == -2 ? -99 : (orderB == -3 ? 100 : orderB));
- return Integer.compare(sortA, sortB);
- });
- // 遍历所有主表,从明细表获取附件URL进行合并
- for (CostProjectTaskMaterialSummary summary : allSummaryList) {
- logger.info("合并资料:{}", summary.getMaterialName());
- List<CostProjectTaskMaterialSummaryDetail> detailList = summary.getDetailList();
- if (detailList != null && !detailList.isEmpty()) {
- detailList.sort(Comparator.comparing(d -> d.getOrderNum() != null ? d.getOrderNum() : 0));
- for (CostProjectTaskMaterialSummaryDetail detail : detailList) {
- if (StringUtil.isNotEmpty(detail.getAttachmentUrl())) {
- isFirstDocument = mergeDocumentFile(document, detail.getAttachmentUrl(), isFirstDocument);
- }
- }
- }
- }
- // 生成输出文件路径
- String fileName = FileUploadUtil.generateFileName("卷宗_" + taskId + ".docx");
- String outputPath = FileUploadUtil.generateSavePath(
- EipConfig.getUploadPath(), fileName, "docx");
- // 确保目录存在
- java.io.File outputFile = new java.io.File(outputPath);
- if (!outputFile.getParentFile().exists()) {
- outputFile.getParentFile().mkdirs();
- }
- // 保存Word文档
- FileOutputStream out = new FileOutputStream(outputPath);
- document.write(out);
- out.close();
- document.close();
- // 生成访问URL
- String archiveUrl = FileUploadUtil.getPathFileName(outputPath, fileName);
- logger.info("Word卷宗生成完成,任务ID:{},URL:{}", taskId, archiveUrl);
- // 更新任务的卷宗URL
- if (task != null) {
- task.setArchiveUrl(archiveUrl);
- task.setArchiveStatus("2");
- task.setArchiveTime(LocalDateTime.now());
- costProjectTaskManager.updateById(task);
- logger.info("卷宗URL已更新,任务ID:{}", taskId);
- }
- } catch (Exception e) {
- if (task != null) {
- task.setArchiveStatus("3");
- costProjectTaskManager.updateById(task);
- }
- logger.error("生成Word卷宗失败,任务ID:,错误:{}", taskId, e.getMessage(), e);
- }
- }
- /**
- * 合并单个文档文件到主文档(支持Word、PDF、Excel等多种格式)
- *
- * @param document 主文档
- * @param fileUrl 文件URL(如:/profile/upload/20251116/xxx.docx)
- * @param isFirstDocument 是否是第一个文档
- * @return 是否是第一个文档(用于下次调用)
- */
- private boolean mergeDocumentFile(XWPFDocument document, String fileUrl, boolean isFirstDocument) {
- try {
- String filePath = fileUrl;
- // 处理路径:/profile 开头的路径需要替换为实际路径
- if (filePath.startsWith("/profile")) {
- filePath = EipConfig.getProfile() + filePath.substring(8);
- }
- java.io.File file = new java.io.File(filePath);
- if (!file.exists()) {
- logger.warn("文件不存在:{}(原始路径:{})", filePath, fileUrl);
- return isFirstDocument;
- }
- String lowerCasePath = filePath.toLowerCase();
- // 添加分页符(非第一个文档)
- if (!isFirstDocument) {
- XWPFParagraph pageBreakPara = document.createParagraph();
- XWPFRun pageBreakRun = pageBreakPara.createRun();
- pageBreakRun.addBreak(BreakType.PAGE);
- }
- // 根据文件类型处理
- if (lowerCasePath.endsWith(".docx") || lowerCasePath.endsWith(".doc")) {
- mergeWordDocument(document, filePath);
- } else if (lowerCasePath.endsWith(".pdf")) {
- mergePdfDocument(document, filePath);
- } else if (lowerCasePath.endsWith(".xlsx") || lowerCasePath.endsWith(".xls")) {
- mergeExcelDocument(document, filePath);
- } else {
- logger.warn("不支持的文件格式:{}", fileUrl);
- return isFirstDocument;
- }
- return false;
- } catch (Exception e) {
- logger.error("合并文件失败:{},错误:{}", fileUrl, e.getMessage(), e);
- return isFirstDocument;
- }
- }
- /**
- * 合并Word文档
- */
- private void mergeWordDocument(XWPFDocument document, String filePath) throws Exception {
- java.io.FileInputStream fis = new java.io.FileInputStream(filePath);
- XWPFDocument sourceDoc = new XWPFDocument(fis);
- org.openxmlformats.schemas.wordprocessingml.x2006.main.CTBody srcBody = sourceDoc.getDocument().getBody();
- org.openxmlformats.schemas.wordprocessingml.x2006.main.CTBody destBody = document.getDocument().getBody();
- for (org.apache.xmlbeans.XmlObject obj : srcBody.selectPath("./*")) {
- if (obj instanceof org.openxmlformats.schemas.wordprocessingml.x2006.main.CTP) {
- org.openxmlformats.schemas.wordprocessingml.x2006.main.CTP newP = destBody.addNewP();
- newP.set(obj.copy());
- } else if (obj instanceof org.openxmlformats.schemas.wordprocessingml.x2006.main.CTTbl) {
- org.openxmlformats.schemas.wordprocessingml.x2006.main.CTTbl newTbl = destBody.addNewTbl();
- newTbl.set(obj.copy());
- }
- }
- sourceDoc.close();
- fis.close();
- }
- /**
- * 合并PDF文档(转换为图片后插入)
- */
- private void mergePdfDocument(XWPFDocument document, String filePath) throws Exception {
- try {
- PDDocument pdfDoc = PDDocument.load(new java.io.File(filePath));
- org.apache.pdfbox.rendering.PDFRenderer renderer = new org.apache.pdfbox.rendering.PDFRenderer(pdfDoc);
- for (int i = 0; i < pdfDoc.getNumberOfPages(); i++) {
- java.awt.image.BufferedImage image = renderer.renderImageWithDPI(i, 200);
- java.io.ByteArrayOutputStream baos = new java.io.ByteArrayOutputStream();
- javax.imageio.ImageIO.write(image, "png", baos);
- byte[] imageBytes = baos.toByteArray();
- baos.close();
- XWPFParagraph para = document.createParagraph();
- XWPFRun run = para.createRun();
- java.io.ByteArrayInputStream bais = new java.io.ByteArrayInputStream(imageBytes);
- run.addPicture(bais, org.apache.poi.xwpf.usermodel.Document.PICTURE_TYPE_PNG,
- "pdf_page_" + i + ".png", org.apache.poi.util.Units.toEMU(410), org.apache.poi.util.Units.toEMU(600));
- bais.close();
- para.createRun().addBreak();
- if (i < pdfDoc.getNumberOfPages() - 1) {
- XWPFParagraph pageBreak = document.createParagraph();
- XWPFRun pageBreakRun = pageBreak.createRun();
- pageBreakRun.addBreak(BreakType.PAGE);
- }
- }
- pdfDoc.close();
- logger.info("PDF文件已合并:{}", filePath);
- } catch (Exception e) {
- logger.error("合并PDF失败:{},错误:{}", filePath, e.getMessage());
- XWPFParagraph para = document.createParagraph();
- XWPFRun run = para.createRun();
- run.setText("[PDF文件:" + new java.io.File(filePath).getName() + " - 无法嵌入]");
- }
- }
- /**
- * 合并Excel文档(转换为表格后插入)
- */
- private void mergeExcelDocument(XWPFDocument document, String filePath) throws Exception {
- try {
- org.apache.poi.ss.usermodel.Workbook workbook = org.apache.poi.ss.usermodel.WorkbookFactory.create(new java.io.File(filePath));
- for (int sheetIndex = 0; sheetIndex < workbook.getNumberOfSheets(); sheetIndex++) {
- org.apache.poi.ss.usermodel.Sheet sheet = workbook.getSheetAt(sheetIndex);
- if (sheet.getPhysicalNumberOfRows() == 0) continue;
- int rows = sheet.getPhysicalNumberOfRows();
- int cols = 0;
- for (int i = 0; i < rows; i++) {
- org.apache.poi.ss.usermodel.Row row = sheet.getRow(i);
- if (row != null && row.getPhysicalNumberOfCells() > cols) {
- cols = row.getPhysicalNumberOfCells();
- }
- }
- if (cols == 0) cols = 1;
- XWPFTable table = document.createTable(rows, cols);
- table.setStyleID("TableGrid");
- for (int i = 0; i < rows; i++) {
- org.apache.poi.ss.usermodel.Row excelRow = sheet.getRow(i);
- XWPFTableRow wordRow = table.getRow(i);
- if (excelRow != null) {
- for (int j = 0; j < cols; j++) {
- org.apache.poi.ss.usermodel.Cell cell = excelRow.getCell(j);
- String cellValue = cell != null ? cell.toString() : "";
- XWPFTableCell wordCell = wordRow.getCell(j);
- wordCell.setText(cellValue);
- }
- }
- }
- if (sheetIndex < workbook.getNumberOfSheets() - 1) {
- XWPFParagraph pageBreak = document.createParagraph();
- XWPFRun pageBreakRun = pageBreak.createRun();
- pageBreakRun.addBreak(BreakType.PAGE);
- }
- }
- workbook.close();
- logger.info("Excel文件已合并:{}", filePath);
- } catch (Exception e) {
- logger.error("合并Excel失败:{},错误:{}", filePath, e.getMessage());
- XWPFParagraph para = document.createParagraph();
- XWPFRun run = para.createRun();
- run.setText("[Excel文件:" + new java.io.File(filePath).getName() + " - 无法嵌入,请查看原文件]");
- }
- }
- /**
- * 更新单个资料归纳主表的总页数
- *
- * @param masterId 主表ID
- */
- public void updateMasterTotalPageCount(String masterId) {
- try {
- CostProjectTaskMaterialSummary summary = costProjectTaskMaterialSummaryManager.getById(masterId);
- if (summary == null) {
- logger.warn("资料归纳主表不存在,ID:{}", masterId);
- return;
- }
- int totalPageCount = 0;
- // 查询该主表的所有明细
- List<CostProjectTaskMaterialSummaryDetail> detailList = costProjectTaskMaterialSummaryDetailManager.list(
- new LambdaQueryWrapper<CostProjectTaskMaterialSummaryDetail>()
- .eq(CostProjectTaskMaterialSummaryDetail::getMasterId, masterId)
- .eq(CostProjectTaskMaterialSummaryDetail::getIsDeleted, "0")
- );
- // 累加所有明细的页数
- for (CostProjectTaskMaterialSummaryDetail detail : detailList) {
- if (detail.getPageCount() != null) {
- totalPageCount += detail.getPageCount();
- }
- }
- // 更新主表的总页数
- summary.setTotalPageCount(String.valueOf(totalPageCount));
- costProjectTaskMaterialSummaryManager.updateById(summary);
- logger.info("资料归纳【{}】总页数已更新:{}", summary.getMaterialName(), totalPageCount);
- } catch (Exception e) {
- logger.error("更新主表总页数失败,主表ID:{},错误:{}", masterId, e.getMessage(), e);
- }
- }
- /**
- * 统计每个资料归纳主表的总页数(所有明细的页数之和)
- *
- * @param taskId 任务ID
- */
- public void calculatePageCountAsync(String taskId) {
- try {
- logger.info("开始异步统计页数,任务ID:{}", taskId);
- // 查询任务的所有资料归纳主表
- List<CostProjectTaskMaterialSummary> summaryList = costProjectTaskMaterialSummaryManager.listByTaskId(taskId);
- for (CostProjectTaskMaterialSummary summary : summaryList) {
- int totalPageCount = 0;
- // 获取该主表的所有明细
- if (summary.getDetailList() != null && !summary.getDetailList().isEmpty()) {
- for (CostProjectTaskMaterialSummaryDetail detail : summary.getDetailList()) {
- if (StringUtil.isNotEmpty(detail.getAttachmentUrl())) {
- // 统计该明细的页数
- int pageCount = calculateFilePageCount(detail.getAttachmentUrl());
- detail.setPageCount(pageCount);
- costProjectTaskMaterialSummaryDetailManager.updateById(detail);
- // 累加到总页数
- totalPageCount += pageCount;
- }
- }
- }
- // 更新主表的总页数
- summary.setTotalPageCount(String.valueOf(totalPageCount));
- costProjectTaskMaterialSummaryManager.updateById(summary);
- logger.info("资料归纳【{}】统计完成,总页数:{}", summary.getMaterialName(), totalPageCount);
- }
- logger.info("页数统计完成,任务ID:{}", taskId);
- } catch (Exception e) {
- logger.error("统计页数失败,任务ID:{},错误:{}", taskId, e.getMessage(), e);
- }
- }
- /**
- * 计算文件页数(公共方法,可被外部调用)
- *
- * @param fileUrl 文件URL或路径
- * @return 页数
- */
- public int calculateFilePageCount(String fileUrl) {
- try {
- if (StringUtil.isEmpty(fileUrl)) {
- return 0;
- }
- String lowerCaseUrl = fileUrl.toLowerCase();
- if (lowerCaseUrl.endsWith(".doc") || lowerCaseUrl.endsWith(".docx")) {
- return getWordPageCount(fileUrl);
- } else {
- return 1;
- }
- } catch (Exception e) {
- logger.error("计算文件页数失败,文件:{},错误:{}", fileUrl, e.getMessage(), e);
- return 1;
- }
- }
- /**
- * 获取Word文档的页数
- *
- * @param fileUrl 文件URL或路径(如:/profile/upload/20251116/xxx.docx)
- * @return 页数
- */
- private int getWordPageCount(String fileUrl) {
- java.io.FileInputStream fis = null;
- XWPFDocument document = null;
- try {
- String filePath = fileUrl;
- if (filePath.startsWith("/profile")) {
- filePath = EipConfig.getProfile() + filePath.substring(8);
- }
- fis = new java.io.FileInputStream(filePath);
- document = new XWPFDocument(fis);
- // 获取页数(可能为null或0)
- try {
- int pageCount = document.getProperties().getExtendedProperties().getUnderlyingProperties().getPages();
- if (pageCount > 0) {
- return pageCount;
- }
- } catch (Exception e) {
- logger.debug("无法读取Word文档页数属性:{}", e.getMessage());
- }
- // 如果页数属性不可用,通过段落数估算(每页约50行)
- int paragraphCount = document.getParagraphs().size();
- int tableCount = document.getTables().size();
- int estimatedPages = Math.max(1, (paragraphCount + tableCount * 10) / 50);
- return estimatedPages;
- } catch (Exception e) {
- logger.error("读取Word页数失败,文件:{},错误:{}", fileUrl, e.getMessage(), e);
- return 1;
- } finally {
- try {
- if (document != null) {
- document.close();
- }
- if (fis != null) {
- fis.close();
- }
- } catch (Exception e) {
- logger.warn("关闭文件流失败:{}", e.getMessage());
- }
- }
- }
- // ==================== 卷宗校对文书生成功能 ====================
- /**
- * 生成卷宗文书(封面/目录/封底)
- * id为空是新增,id不为空是编辑
- *
- * @param req 生成请求
- * @return 生成的文书URL
- */
- public String generateArchiveDocument(com.hotent.project.req.ArchiveProofreadReq req) throws Exception {
- Integer documentType = req.getDocumentType();
- String existingId = req.getRelatedId();
- // 如果id不为空,从数据库获取已有记录的documentType(id是主表ID)
- if (StringUtil.isNotEmpty(existingId)) {
- CostProjectTaskMaterialSummary existing = costProjectTaskMaterialSummaryManager.getById(existingId);
- if (existing == null) {
- throw new RuntimeException("主表记录不存在:" + existingId);
- }
- Integer orderNum = existing.getMaterialOrderNum();
- if (orderNum != null && orderNum == -1) {
- documentType = 1;
- } else if (orderNum != null && orderNum == -2) {
- documentType = 2;
- } else if (orderNum != null && orderNum == -3) {
- documentType = 3;
- } else {
- throw new RuntimeException("无效的文书记录");
- }
- }
- String templatePath;
- String documentName;
- switch (documentType) {
- case 1:
- templatePath = coverTemplatePath;
- documentName = "案卷封面";
- if (StringUtil.isEmpty(templatePath)) {
- throw new RuntimeException("案卷封面模板路径未配置");
- }
- break;
- case 2:
- templatePath = catalogTemplatePath;
- documentName = "卷内目录";
- if (StringUtil.isEmpty(templatePath)) {
- throw new RuntimeException("卷内目录模板路径未配置");
- }
- break;
- case 3:
- templatePath = backCoverTemplatePath;
- documentName = "案卷封底";
- if (StringUtil.isEmpty(templatePath)) {
- throw new RuntimeException("案卷封底模板路径未配置");
- }
- break;
- default:
- throw new RuntimeException("不支持的文书类型:" + documentType);
- }
- // 检查模板文件是否存在
- java.io.File templateFile = new java.io.File(templatePath);
- if (!templateFile.exists()) {
- throw new RuntimeException("模板文件不存在:" + templatePath);
- }
- // 生成文书
- String outputUrl = generateDocumentFromTemplate(templatePath, documentName, req);
- // 保存到数据库(主表+明细表)
- int orderNum = -documentType; // -1封面、-2目录、-3封底
- String masterId;
- if (StringUtil.isNotEmpty(existingId)) {
- // 编辑:existingId是主表ID,查找对应的明细记录
- masterId = existingId;
- CostProjectTaskMaterialSummary existingSummary = costProjectTaskMaterialSummaryManager.getById(masterId);
- if (existingSummary != null) {
- // 更新task的卷宗号和归档人
- CostProjectTask task = costProjectTaskManager.getById(existingSummary.getTaskId());
- if (task != null) {
- task.setArchiveNo(req.getArchiveNo());
- task.setArchiveUser(ContextUtil.getCurrentUser().getFullname());
- costProjectTaskManager.updateById(task);
- }
- }
- CostProjectTaskMaterialSummaryDetail existingDetail = costProjectTaskMaterialSummaryDetailManager.getOne(
- new LambdaQueryWrapper<CostProjectTaskMaterialSummaryDetail>()
- .eq(CostProjectTaskMaterialSummaryDetail::getMasterId, masterId)
- .eq(CostProjectTaskMaterialSummaryDetail::getIsDeleted, "0")
- );
- if (existingDetail != null) {
- // 更新已有明细
- existingDetail.setAttachmentUrl(outputUrl);
- existingDetail.setGenerateTime(java.time.LocalDateTime.now());
- costProjectTaskMaterialSummaryDetailManager.updateById(existingDetail);
- } else {
- // 创建新明细
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(masterId);
- detail.setTaskId(req.getTaskId());
- detail.setDocumentName(documentName);
- detail.setFileSource("系统生成电子文书");
- detail.setAttachmentUrl(outputUrl);
- detail.setOrderNum(1);
- detail.setGenerateTime(java.time.LocalDateTime.now());
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- } else {
- // 新增:创建主表记录
- CostProjectTaskMaterialSummary summary = new CostProjectTaskMaterialSummary();
- summary.setTaskId(req.getTaskId());
- summary.setMaterialOrderNum(orderNum);
- summary.setMaterialName(documentName);
- summary.setIsDeleted("0");
- costProjectTaskMaterialSummaryManager.save(summary);
- masterId = summary.getId();
- // 更新task的卷宗号和归档人
- CostProjectTask task = costProjectTaskManager.getById(req.getTaskId());
- if (task != null) {
- task.setArchiveNo(req.getArchiveNo());
- task.setArchiveUser(ContextUtil.getCurrentUser().getAccount());
- costProjectTaskManager.updateById(task);
- }
- // 创建明细记录
- CostProjectTaskMaterialSummaryDetail detail = new CostProjectTaskMaterialSummaryDetail();
- detail.setMasterId(masterId);
- detail.setTaskId(req.getTaskId());
- detail.setDocumentName(documentName);
- detail.setFileSource("系统生成电子文书");
- detail.setAttachmentUrl(outputUrl);
- detail.setOrderNum(1);
- detail.setGenerateTime(java.time.LocalDateTime.now());
- detail.setIsDeleted("0");
- costProjectTaskMaterialSummaryDetailManager.save(detail);
- }
- return outputUrl;
- }
- /**
- * 根据模板生成文书
- *
- * @param templatePath 模板路径
- * @param documentName 文书名称
- * @param req 请求参数
- * @return 生成的文书URL
- */
- private String generateDocumentFromTemplate(String templatePath, String documentName,
- com.hotent.project.req.ArchiveProofreadReq req) throws Exception {
- java.io.FileInputStream fis = null;
- XWPFDocument document = null;
- java.io.FileOutputStream fos = null;
- try {
- // 读取模板
- fis = new java.io.FileInputStream(templatePath);
- document = new XWPFDocument(fis);
- // 构建替换映射
- Map<String, String> replacements = buildReplacementMap(req);
- // 根据文书类型进行不同处理
- switch (req.getDocumentType()) {
- case 1:
- // 案卷封面
- generateCoverDocument(document, replacements);
- break;
- case 2:
- // 卷内目录
- generateCatalogDocument(document, replacements, req.getTaskId());
- break;
- case 3:
- // 案卷封底
- generateBackCoverDocument(document, replacements);
- break;
- }
- // 生成输出文件路径
- String fileName = FileUploadUtil.generateFileName(documentName + ".docx");
- String outputPath = FileUploadUtil.generateSavePath(
- EipConfig.getUploadPath(), fileName, "docx");
- // 确保目录存在
- java.io.File outputFile = new java.io.File(outputPath);
- if (!outputFile.getParentFile().exists()) {
- outputFile.getParentFile().mkdirs();
- }
- // 写入文件
- fos = new java.io.FileOutputStream(outputPath);
- document.write(fos);
- // 返回访问URL
- return FileUploadUtil.getPathFileName(outputPath, fileName);
- } finally {
- // 关闭资源
- try {
- if (fos != null) fos.close();
- if (document != null) document.close();
- if (fis != null) fis.close();
- } catch (Exception e) {
- logger.warn("关闭文件流失败:{}", e.getMessage());
- }
- }
- }
- /**
- * 构建替换映射
- * 自动从数据库获取:年份、监审项目名称、被监审单位、监审期间(开始-结束年度)、监审人员、办结时间
- * 需要用户传递:价格主管部门、卷宗号、保管期间周期、立卷人、立卷日期、检查人、检查日期、备注
- */
- private Map<String, String> buildReplacementMap(com.hotent.project.req.ArchiveProofreadReq req) {
- Map<String, String> map = new java.util.HashMap<>();
- // 从数据库获取任务信息
- CostProjectTask task = costProjectTaskManager.getById(req.getTaskId());
- // 从数据库获取立项审批信息(包含监审组人员)
- CostProjectApproval approval = costProjectApprovalManager.getOne(
- new LambdaQueryWrapper<CostProjectApproval>()
- .eq(CostProjectApproval::getProjectId, task.getProjectId())
- );
- // ========== 自动获取的字段 ==========
- Org org = orgManager.getById(approval.getOrgId());
- map.put("{价格主管部门或成本监审机构}", org.getName());
- map.put("{年份}", task.getYear());
- map.put("{监审项目名称}", task.getProjectName());
- map.put("{被监审单位}", task.getAuditedUnitName());
- // 监审期间(解析开始-结束年度,格式如:2024,2025,2023 逗号分隔)
- String startYear = "";
- String endYear = "";
- String auditPeriod = task.getAuditPeriod();
- if (StringUtil.isNotEmpty(auditPeriod)) {
- String[] years = auditPeriod.split(",");
- int minYear = Integer.MAX_VALUE;
- int maxYear = Integer.MIN_VALUE;
- for (String year : years) {
- try {
- int y = Integer.parseInt(year.trim());
- if (y < minYear) minYear = y;
- if (y > maxYear) maxYear = y;
- } catch (NumberFormatException e) {
- }
- }
- if (minYear != Integer.MAX_VALUE) {
- startYear = String.valueOf(minYear);
- endYear = String.valueOf(maxYear);
- }
- }
- map.put("{监审开始年度}", startYear);
- map.put("{监审结束年度}", endYear);
- // 监审组负责人及人员(将ID转换为姓名)
- String auditGroupNames = "";
- if (approval != null && StringUtil.isNotEmpty(approval.getAuditGroup())) {
- String[] userIds = approval.getAuditGroup().split(",");
- StringBuilder names = new StringBuilder();
- for (String userId : userIds) {
- try {
- User user = userManager.get(userId.trim());
- if (user != null) {
- if (names.length() > 0) {
- names.append(",");
- }
- names.append(user.getFullname());
- }
- } catch (Exception e) {
- }
- }
- auditGroupNames = names.toString();
- }
- map.put("{监审组负责人及人员}", auditGroupNames);
- // 监审办结时间(任务状态为办结时,取更新时间,格式:xxxx年xx月)
- String auditEndTime = "";
- if ("400".equals(task.getStatus()) && task.getUpdateTime() != null) {
- auditEndTime = task.getUpdateTime().getYear() + "年" + task.getUpdateTime().getMonthValue() + "月";
- }
- map.put("{监审办结时间}", auditEndTime);
- // ========== 需要用户传递的字段 ==========
- map.put("{卷宗号}", req.getArchiveNo() != null ? req.getArchiveNo() : "");
- map.put("{保管期间周期}", req.getRetentionPeriod() != null ? req.getRetentionPeriod() : "");
- // ========== 卷宗统计信息 ==========
- // 获取14个资料归纳的总页数
- List<CostProjectTaskMaterialSummary> summaryList = costProjectTaskMaterialSummaryManager.listByTaskId(req.getTaskId());
- summaryList = summaryList.stream()
- .filter(s -> s.getMaterialOrderNum() != null && s.getMaterialOrderNum() > 0)
- .collect(Collectors.toList());
- int totalPageCount = 0;
- for (CostProjectTaskMaterialSummary summary : summaryList) {
- if (summary.getTotalPageCount() != null) {
- try {
- totalPageCount += Integer.parseInt(summary.getTotalPageCount());
- } catch (NumberFormatException e) {
- }
- }
- }
- map.put("{卷宗件数}", "1"); // 默认1件
- map.put("{卷宗页数}", String.valueOf(totalPageCount));
- map.put("{第几件}", "1"); // 默认第1件
- map.put("{备注}", req.getRemark());
- return map;
- }
- /**
- * 生成案卷封面
- */
- private void generateCoverDocument(XWPFDocument document, Map<String, String> replacements) {
- SmartTemplateWriter.writeToTemplate(document, replacements);
- }
- /**
- * 生成卷内目录(只填充表格,不替换占位符)
- */
- private void generateCatalogDocument(XWPFDocument document, Map<String, String> replacements, String taskId) {
- // 获取资料归纳列表,生成目录表格
- List<CostProjectTaskMaterialSummary> summaryList = costProjectTaskMaterialSummaryManager.listByTaskId(taskId);
- // 过滤掉封面、目录、封底(负数序号)
- summaryList = summaryList.stream()
- .filter(s -> s.getMaterialOrderNum() != null && s.getMaterialOrderNum() > 0)
- .sorted(Comparator.comparing(CostProjectTaskMaterialSummary::getMaterialOrderNum))
- .collect(Collectors.toList());
- // 构建目录数据
- List<CompleteTemplateProcessor.TableRowData> tableDataList = new java.util.ArrayList<>();
- int currentPage = 1;
- for (CostProjectTaskMaterialSummary summary : summaryList) {
- CompleteTemplateProcessor.TableRowData rowData =
- new CompleteTemplateProcessor.TableRowData();
- rowData.setDocumentName(summary.getMaterialName());
- int pageCount = 0;
- if (summary.getTotalPageCount() != null) {
- try {
- pageCount = Integer.parseInt(summary.getTotalPageCount());
- } catch (NumberFormatException e) {
- pageCount = 0;
- }
- }
- rowData.setPageCount(pageCount);
- // 计算页码范围作为备注
- if (pageCount > 0) {
- rowData.setRemark(currentPage + "-" + (currentPage + pageCount - 1));
- currentPage += pageCount;
- } else {
- rowData.setRemark("—");
- }
- tableDataList.add(rowData);
- }
- // 只填充表格数据,
- if (!tableDataList.isEmpty()) {
- processTableData(document, tableDataList);
- }
- }
- /**
- * 生成案卷封底
- */
- private void generateBackCoverDocument(XWPFDocument document, Map<String, String> replacements) {
- SmartTemplateWriter.writeToTemplate(document, replacements);
- }
- /**
- * 处理目录表格数据
- */
- private void processTableData(XWPFDocument document, List<CompleteTemplateProcessor.TableRowData> dataList) {
- List<XWPFTable> tables = document.getTables();
- if (tables.isEmpty()) {
- logger.warn("未找到表格");
- return;
- }
- XWPFTable table = tables.get(0);
- // 找到模板行(第二行,第一行是表头)
- int templateRowIndex = 0;
- if (table.getRows().size() <= templateRowIndex) {
- logger.warn("表格行数不足");
- return;
- }
- // 获取模板行的单元格数量
- int cellCount = table.getRow(templateRowIndex).getTableCells().size();
- // 删除模板行
- table.removeRow(templateRowIndex);
- // 从模板行位置开始插入数据行
- for (int i = 0; i < dataList.size(); i++) {
- CompleteTemplateProcessor.TableRowData data = dataList.get(i);
- XWPFTableRow newRow = table.insertNewTableRow(templateRowIndex + i);
- // 创建单元格
- for (int j = 0; j < cellCount; j++) {
- newRow.addNewTableCell();
- }
- fillTableRow(newRow, i + 1, data);
- }
- }
- /**
- * 填充表格行数据
- */
- private void fillTableRow(XWPFTableRow row, int sequence,
- CompleteTemplateProcessor.TableRowData data) {
- List<XWPFTableCell> cells = row.getTableCells();
- if (cells.size() >= 4) {
- setCellText(cells.get(0), String.valueOf(sequence));
- setCellText(cells.get(1), data.getDocumentName());
- setCellText(cells.get(2), data.getPageCount() > 0 ? String.valueOf(data.getPageCount()) : "");
- setCellText(cells.get(3), data.getRemark() != null ? data.getRemark() : "");
- }
- }
- /**
- * 设置单元格文本
- */
- private void setCellText(XWPFTableCell cell, String text) {
- // 清除现有内容
- for (int i = cell.getParagraphs().size() - 1; i >= 0; i--) {
- cell.removeParagraph(i);
- }
- // 添加新内容
- XWPFParagraph paragraph = cell.addParagraph();
- XWPFRun run = paragraph.createRun();
- run.setText(text);
- paragraph.setAlignment(ParagraphAlignment.CENTER);
- }
- }
|