Przeglądaj źródła

档案结论生成PDF

qianxb 1 rok temu
rodzic
commit
859aa01446
14 zmienionych plików z 706 dodań i 40 usunięć
  1. 3 0
      blade-service-api/blade-archive-api/src/main/java/org/springblade/archive/entity/ArchiveExpertConclusion.java
  2. 1 1
      blade-service-api/blade-archive-api/src/main/java/org/springblade/archive/feign/ArchiveExpertConclusionClient.java
  3. 27 0
      blade-service-api/blade-archive-api/src/main/java/org/springblade/archive/vo/ExpertInfoVO.java
  4. 1 1
      blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchiveExpertConclusionController.java
  5. 1 1
      blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchiveExpertScoreController.java
  6. 14 16
      blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchivesAutoController.java
  7. 2 2
      blade-service/blade-archive/src/main/java/org/springblade/archive/feign/ArchiveExpertConclusionClientImpl.java
  8. 1 1
      blade-service/blade-archive/src/main/java/org/springblade/archive/mapper/ArchivesAutoMapper.xml
  9. 1 1
      blade-service/blade-archive/src/main/java/org/springblade/archive/service/IArchiveExpertConclusionService.java
  10. 243 13
      blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchiveExpertConclusionServiceImpl.java
  11. 38 3
      blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchiveExpertScoreServiceImpl.java
  12. 230 0
      blade-service/blade-archive/src/main/java/org/springblade/archive/utils/ItextPdfUtils.java
  13. 128 0
      blade-service/blade-archive/src/main/java/org/springblade/archive/utils/MyPdfPageHelper.java
  14. 16 1
      blade-service/blade-business/src/main/java/org/springblade/business/controller/TaskController.java

+ 3 - 0
blade-service-api/blade-archive-api/src/main/java/org/springblade/archive/entity/ArchiveExpertConclusion.java

@@ -71,4 +71,7 @@ public class ArchiveExpertConclusion extends BaseEntity {
     @ApiModelProperty("任务")
     private Long taskId;
 
+    @ApiModelProperty("此轮抽检专家id,逗号分隔")
+    private String expertIds;
+
 }

+ 1 - 1
blade-service-api/blade-archive-api/src/main/java/org/springblade/archive/feign/ArchiveExpertConclusionClient.java

@@ -14,5 +14,5 @@ public interface ArchiveExpertConclusionClient {
     String API_PREFIX = "/api/archive/archiveExpertConclusion";
 
     @GetMapping(API_PREFIX + "/saveBaseTableInfo")
-    R saveBaseTableInfo(@RequestParam Long projectId, @RequestParam String appUrl,@RequestParam Long taskId);
+    R saveBaseTableInfo(@RequestParam Long projectId, @RequestParam String appUrl,@RequestParam Long taskId,@RequestParam String expertIds);
 }

+ 27 - 0
blade-service-api/blade-archive-api/src/main/java/org/springblade/archive/vo/ExpertInfoVO.java

@@ -0,0 +1,27 @@
+package org.springblade.archive.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @Param   档案抽检专家信息VO
+ * @Author wangwl
+ * @Date 2024/1/18 14:57
+ **/
+@Data
+public class ExpertInfoVO {
+    @ApiModelProperty("姓名")
+    private String name;
+
+    @ApiModelProperty("职位")
+    private String position;
+
+    @ApiModelProperty("是否为组长,0否1是")
+    private Integer isLeader;
+
+    @ApiModelProperty("身份证号")
+    private String idNumber;
+
+    @ApiModelProperty("手机号")
+    private String phone;
+}

+ 1 - 1
blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchiveExpertConclusionController.java

@@ -169,6 +169,6 @@ public class ArchiveExpertConclusionController extends BladeController {
     public R submitTable(@RequestBody ArchiveExpertConclusion conclusion) {
         conclusionService.updateById(conclusion);
         conclusionService.submitTable(conclusion);
-        return R.data("提交成功");
+        return R.data("结论生成成功");
     }
 }

+ 1 - 1
blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchiveExpertScoreController.java

@@ -53,7 +53,7 @@ public class ArchiveExpertScoreController extends BladeController {
 
     @GetMapping("/test")
     public R test( Long projectId,Long conclusionId) throws Exception {
-        scoreService.buildScorePdf(projectId,conclusionId);
+        scoreService.saveBaseScoreInfo(projectId,conclusionId);
         return R.data("修改成功");
     }
 

+ 14 - 16
blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchivesAutoController.java

@@ -913,25 +913,25 @@ public class ArchivesAutoController extends BladeController {
 		return R.data(vo);
 	}
 
-	/**
-	 * 在线excel 档案修改回调
-	 */
-	@PostMapping(value = "/callbackSave")
-	@ApiOperation(value = "onlyOffice保存回调", notes = "onlyOffice保存回调")
-	@ApiOperationSupport(order = 37)
-	@ResponseBody
-	public ExcelEditCallback callbackSave(@RequestBody ExcelEditCallback callback, HttpServletRequest request) {
-		String projectId = request.getParameter("projectId");
-		callback.setProjectId(Long.parseLong(projectId));
-		return archivesAutoService.callbackSave(callback);
-	}
+//	/**
+//	 * 在线excel 档案修改回调
+//	 */
+//	@PostMapping(value = "/callbackSave")
+//	@ApiOperation(value = "onlyOffice保存回调", notes = "onlyOffice保存回调")
+//	@ApiOperationSupport(order = 37)
+//	@ResponseBody
+//	public ExcelEditCallback callbackSave(@RequestBody ExcelEditCallback callback, HttpServletRequest request) {
+//		String projectId = request.getParameter("projectId");
+//		callback.setProjectId(Long.parseLong(projectId));
+//		return archivesAutoService.callbackSave(callback);
+//	}
 
 	/**
 	 * 档案预警-分页查询
 	 */
 	@PostMapping("/warningPage")
-	@ApiOperationSupport(order = 36)
-	@ApiOperation(value = "在线验收-编写报告", notes = "传入项目id,节点和整改状态,返回分页信息")
+	@ApiOperationSupport(order = 40)
+	@ApiOperation(value = "档案预警-分页查询", notes = "传入项目id,节点和整改状态,返回分页信息")
 	@ApiImplicitParams(value = {
 			@ApiImplicitParam(name = "rectification", value = "1待整改2已整改", required = true),
 			@ApiImplicitParam(name = "nodeId", value = "节点id", required = true),
@@ -944,6 +944,4 @@ public class ArchivesAutoController extends BladeController {
 	}
 
 
-
-
 }

+ 2 - 2
blade-service/blade-archive/src/main/java/org/springblade/archive/feign/ArchiveExpertConclusionClientImpl.java

@@ -16,7 +16,7 @@ public class ArchiveExpertConclusionClientImpl implements ArchiveExpertConclusio
 
 
     @Override
-    public R saveBaseTableInfo(Long projectId, String appUrl,Long taskId) {
-        return conclusionService.saveBaseTableInfo(projectId,appUrl,taskId);
+    public R saveBaseTableInfo(Long projectId, String appUrl,Long taskId,String expertIds) {
+        return conclusionService.saveBaseTableInfo(projectId,appUrl,taskId,expertIds);
     }
 }

+ 1 - 1
blade-service/blade-archive/src/main/java/org/springblade/archive/mapper/ArchivesAutoMapper.xml

@@ -1144,7 +1144,7 @@
           and (atc.id = #{nodeId} or FIND_IN_SET(#{nodeId}, atc.ancestors))
     </select>
     <select id="getSpotCheck" resultType="org.springblade.archive.vo.ArchiveWarningVO">
-        select GROUP_CONCAT(aei.opinion) as allopinion,aei.archive_name ,aei.node_id,1 as sourceType
+        select GROUP_CONCAT(aei.opinion) as allopinion,aei.archive_name ,aei.node_id,1 as sourceType,
                (select uaf.file_name from u_archive_file uaf WHERE uaf.id = aei.file_id) as fileName,
                (select uaf.file_url from u_archive_file uaf WHERE uaf.id = aei.file_id) as fileUrl
         from m_archive_tree_contract atc join u_archive_expert_inspection aei on aei.node_id  = atc.id

+ 1 - 1
blade-service/blade-archive/src/main/java/org/springblade/archive/service/IArchiveExpertConclusionService.java

@@ -12,7 +12,7 @@ public interface IArchiveExpertConclusionService extends BaseService<ArchiveExpe
 
 
     //验收申请审批通过,创建当前报表基本信息
-    R saveBaseTableInfo(Long projectId,String appUrl,Long taskId);
+    R saveBaseTableInfo(Long projectId,String appUrl,Long taskId,String expertIds);
 
     Boolean getAppStatus(Long projectId);
 

+ 243 - 13
blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchiveExpertConclusionServiceImpl.java

@@ -3,6 +3,13 @@ package org.springblade.archive.service.impl;
 
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+import com.itextpdf.text.Document;
+import com.itextpdf.text.Font;
+import com.itextpdf.text.PageSize;
+import com.itextpdf.text.pdf.BaseFont;
+import com.itextpdf.text.pdf.PdfPCell;
+import com.itextpdf.text.pdf.PdfPTable;
+import com.itextpdf.text.pdf.PdfWriter;
 import lombok.AllArgsConstructor;
 import org.apache.commons.lang.StringUtils;
 import org.springblade.archive.entity.ArchiveExpertConclusion;
@@ -11,17 +18,29 @@ import org.springblade.archive.mapper.ArchiveExpertConclusionMapper;
 import org.springblade.archive.mapper.ArchiveExpertScoreMapper;
 import org.springblade.archive.service.IArchiveExpertConclusionService;
 import org.springblade.archive.service.IArchiveExpertScoreService;
+import org.springblade.archive.utils.ItextPdfUtils;
+import org.springblade.archive.utils.MyPdfPageHelper;
 import org.springblade.common.utils.SnowFlakeUtil;
 import org.springblade.core.log.exception.ServiceException;
 import org.springblade.core.mp.base.BaseServiceImpl;
+import org.springblade.core.oss.model.BladeFile;
 import org.springblade.core.secure.utils.AuthUtil;
 import org.springblade.core.tool.api.R;
+import org.springblade.core.tool.utils.Func;
 import org.springblade.manager.entity.ProjectInfo;
 import org.springblade.manager.feign.ProjectClient;
+import org.springblade.resource.feign.NewIOSSClient;
+import org.springblade.system.user.entity.User;
+import org.springblade.system.user.feign.IUserClient;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 
+import java.io.FileOutputStream;
+import java.text.SimpleDateFormat;
+import java.util.Date;
 import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
 
 @Service
 @AllArgsConstructor
@@ -31,9 +50,18 @@ public class ArchiveExpertConclusionServiceImpl extends BaseServiceImpl<ArchiveE
 
     private final ProjectClient projectClient;
 
+    private final IUserClient userClient;
+
+    private final NewIOSSClient newIOSSClient;
+    //表格高度
+    private static int high = 20;
+    //表格宽度
+    private static int widthPercentage = 80;
+
+
     @Override
     @Transactional
-    public R saveBaseTableInfo(Long projectId, String appUrl,Long taskId) {
+    public R saveBaseTableInfo(Long projectId, String appUrl,Long taskId,String expertIds) {
         //判断当前项目下是否存在抽检中的数据
         long count = this.count(new LambdaUpdateWrapper<ArchiveExpertConclusion>()
                 .eq(ArchiveExpertConclusion::getProjectId, projectId)
@@ -191,26 +219,228 @@ public class ArchiveExpertConclusionServiceImpl extends BaseServiceImpl<ArchiveE
     @Override
     @Transactional
     public void submitTable(ArchiveExpertConclusion conclusion) {
-        //生成结论pdf
-        //判断是否追加
-        if (conclusion.getIsBuildScore() == 1) {
-            String scoreUrl;
-            //调用生成
-            try {
-                 scoreUrl = scoreService.buildScorePdf(conclusion.getProjectId(), conclusion.getId());
-            }catch (Exception e){
-                throw new ServiceException("创建专家评分表PDF失败");
-            }
-            if (StringUtils.isNotBlank(scoreUrl)){
-                //合并PDF
+        String pdfUrl = "";
+        try {
+            //生成结论pdf
+            pdfUrl = buildPdf(conclusion);
+            if (StringUtils.isBlank(pdfUrl)){
+                throw new ServiceException("");
             }
+        }catch (Exception e){
+            throw new ServiceException("生成PDF失败");
         }
         //PDF电签
+        try {
+//            pdfUrl = ;
+        }catch (Exception e){
+            throw new ServiceException("PDF电签失败");
+        }
         //修改状态,插入结论PDF
+        conclusion.setTableUrl(pdfUrl);
         conclusion.setStatus(2);
         this.updateById(conclusion);
     }
 
+    private String buildPdf(ArchiveExpertConclusion conclusion) throws Exception {
+        //获取评分基础数据
+        List<ArchiveExpertScore> list1 = scoreService.list(new LambdaQueryWrapper<ArchiveExpertScore>()
+                .eq(ArchiveExpertScore::getProjectId, conclusion.getProjectId())
+                .eq(ArchiveExpertScore::getConclusionId, conclusion.getId()));
+        Map<Integer, List<ArchiveExpertScore>> map = list1.stream().collect(Collectors.groupingBy(ArchiveExpertScore::getUnitType));
+        //根据专家信息获取到具体的user
+        String expertIds = conclusion.getExpertIds();
+        if (StringUtils.isBlank(expertIds)){
+            throw new ServiceException("获取专家账号失败");
+        }
+        List<Long> userIds = Func.toLongList(expertIds);
+        List<User> users = userClient.userInfoByIds(userIds);
+        //获取专家组长
+        User us = null;
+        for (User user : users) {
+            if ("1656191696348082177".equals(user.getRoleId())){
+                us = user;
+            }
+        }
+        if (us == null){
+            throw new ServiceException("未获取到专家组长");
+        }
+        //新建一个pdf文档对象,前一个参数是纸张大小,后四个为边距
+        Document document = new Document(PageSize.A4, 10, 10, 80, 85);
+        //文件地址
+        String localFile = "C:\\Users\\泓创研发01\\Desktop\\"+conclusion.getId()+".pdf";
+        //建立一个书写器
+        PdfWriter writer = PdfWriter.getInstance(document, new FileOutputStream(localFile));
+        //页尾
+        MyPdfPageHelper helper = new MyPdfPageHelper();
+        writer.setPageEvent(helper);
+        document.open();
+        //创建字体
+        BaseFont baseFont2 =BaseFont.createFont("C:/WINDOWS/Fonts/simsun.ttc,0", BaseFont.IDENTITY_H,BaseFont.NOT_EMBEDDED);
+        //字体对象,这里可以创建一个方法
+        Font sigFont = new Font(baseFont2, 0.1F, Font.NORMAL); //大小为0.1的正常字体
+        Font size13font = new Font(baseFont2, 13, Font.NORMAL); //大小为13的正常字体
+        Font size13bold = new Font(baseFont2, 13, Font.BOLD); //大小为13的粗字体
+        Font size14bold = new Font(baseFont2, 14, Font.BOLD); //大小为14的粗字体
+        Font size17bold = new Font(baseFont2, 17, Font.BOLD);  //大小为17的正常字体
+
+        String firstText = "重庆渝北至长寿高速公路(渝长高速公路扩能)";
+        String secondText = "档案专项验收意见";
+        ItextPdfUtils.tableHeader(document,size17bold,firstText);
+        ItextPdfUtils.tableHeader(document,size17bold,secondText);
+        ItextPdfUtils.blankRow(document,size13font,20);
+        //创建第二行
+        ItextPdfUtils.tableText(document,size13font,conclusion.getForeword());
+        String ss ="一、项目概况";
+        ItextPdfUtils.rowHeader(document,ss,size14bold,83,20);
+        ItextPdfUtils.tableText(document,size13font,conclusion.getGeneralSituation());
+        String ss2 ="二、项目档案管理情况";
+        ItextPdfUtils.rowHeader(document,ss2,size14bold,83,20);
+        ItextPdfUtils.tableText(document,size13font,conclusion.getAdminCondition());
+        String ss3 ="三、存在问题及建议";
+        ItextPdfUtils.rowHeader(document,ss3,size14bold,83,20);
+        ItextPdfUtils.tableText(document,size13font,conclusion.getQuestionSuggest());
+        ItextPdfUtils.blankRow(document,size13font,60);
+        //落款项目
+        ItextPdfUtils.endRight(document,size13font,"重庆渝北至长寿高速公路(渝长高速公路扩能)",widthPercentage);
+        //落款档案验收组
+        ItextPdfUtils.endRight(document,size13font,"档案验收组",60);
+        //落款日期
+        ItextPdfUtils.endRight(document,size13font,new SimpleDateFormat("yyyy年M月dd日").format(new Date()),63);
+        if (conclusion.getIsBuildScore() == 1) {
+            //评分表
+            //该数组是每个表格的宽度
+            float[] floats = new float[5];
+            floats[0] = 0.48f;
+            floats[1] = 0.13f;
+            floats[2] = 0.13f;
+            floats[3] = 0.13f;
+            floats[4] = 0.13f;
+            //末尾表格
+            float[] floats2 = new float[2];
+            floats2[0] = 0.48f;
+            floats2[1] = 0.52f;
+            //为每个单位生成评分表,
+            for (int i = 1; i <= 3; i++) {
+                //如果当前单位没有扣分项,则跳过生成当前单位评分表
+                List<ArchiveExpertScore> list = map.get(i);
+                Boolean isMark = false;
+                for (ArchiveExpertScore score : list) {
+                    if (score.getIntegralityDeduction() != 0 || score.getNormativeDeduction() != 0) {
+                        isMark = true;
+                        break;
+                    }
+                }
+                if (!isMark) {
+                    continue;
+                }
+                //换页生成
+                document.newPage();
+                ItextPdfUtils.startLeft(document, size13font, "附件", 80);
+                ItextPdfUtils.blankRow(document, size13font, 10);
+                String title = "项目档案验收评分表";
+                ItextPdfUtils.tableHeader(document, size17bold, title);
+                //设置单位
+                String unitName = "";
+                if (i == 1) {
+                    unitName = "总承包单位";
+                } else if (i == 2) {
+                    unitName = "监理单位";
+                } else {
+                    unitName = "施工单位";
+                }
+                ItextPdfUtils.rowHeader(document, unitName + ":", size13bold, 85, 30);
+                ItextPdfUtils.tableUnit(document, size13bold, unitName, 30);
+                //表头文字
+                String[] name = new String[]{"项目", "完整性", "扣分", "规范性", "扣分"};
+                //创建第二行,并设置第二行中的表格数
+                PdfPTable twoTable = new PdfPTable(name.length);
+                twoTable.setWidthPercentage(widthPercentage);
+                //设置表格的宽度
+                twoTable.setTotalWidth(floats);
+                //循环将表头数据添加到第二行表格中
+                for (int j = 0; j < name.length; j++) {
+                    PdfPCell pdfPCell = ItextPdfUtils.pdfTableStyle7(name[j], size13font, 30);
+                    twoTable.addCell(pdfPCell);
+                }
+                document.add(twoTable);
+                //将数据放入表格中
+
+                int allScore = 0;
+                int allPoints = 0;
+                for (int j = 0; j < list.size(); j++) {
+                    PdfPTable dataTable = new PdfPTable(5);
+                    dataTable.setWidths(floats);
+                    dataTable.setWidthPercentage(widthPercentage);
+                    ArchiveExpertScore score = list.get(j);
+                    dataTable.addCell(ItextPdfUtils.pdfTableStyle7(score.getScoreItem(), size13font, 25));
+                    dataTable.addCell(ItextPdfUtils.pdfTableStyle7(score.getIntegrality() + "", size13font, 25));
+                    dataTable.addCell(ItextPdfUtils.pdfTableStyle7(score.getIntegralityDeduction() + "", size13font, 25));
+                    dataTable.addCell(ItextPdfUtils.pdfTableStyle7(score.getNormative() + "", size13font, 25));
+                    dataTable.addCell(ItextPdfUtils.pdfTableStyle7(score.getNormativeDeduction() + "", size13font, 25));
+                    document.add(dataTable);
+                    allScore += score.getIntegrality() + score.getNormative();
+                    allPoints += score.getIntegralityDeduction() + score.getNormativeDeduction();
+                }
+                //末尾统计行
+                PdfPTable statRow = new PdfPTable(2);
+                statRow.setWidths(floats2);
+                statRow.setWidthPercentage(widthPercentage);
+                PdfPCell leftCell = ItextPdfUtils.pdfTableStyle7("总得分", size13font, 25);
+                statRow.addCell(leftCell);
+                PdfPCell rightCell = ItextPdfUtils.pdfTableStyle7(allScore - allPoints + "", size13font, 25);
+                statRow.addCell(rightCell);
+                document.add(statRow);
+
+            }
+        }
+        //生成签名表
+        document.newPage();
+        ItextPdfUtils.startLeft(document,size13font,"附件",80);
+        ItextPdfUtils.blankRow(document,size13font,10);
+        ItextPdfUtils.tableHeader(document,size17bold,firstText);
+        ItextPdfUtils.tableHeader(document,size17bold,"工程档案验收组成员签字表");
+        ItextPdfUtils.blankRow(document,size13font,30);
+        ItextPdfUtils.rowHeader2(document,"组  长:",size13font,us.getName()+us.getPhone().substring(0,3),sigFont);
+        ItextPdfUtils.blankRow(document,size13font,10);
+        //该数组是每个表格的宽度
+        float[] floats5 = new float[4];
+        floats5[0] = 0.1f;
+        floats5[1] = 0.4f;
+        floats5[2] = 0.25f;
+        floats5[3] = 0.25f;
+        //表头文字
+        String[] name2 = new String[]{"姓名", "单位", "职务职称", "签名"};
+        //创建第二行,并设置第二行中的表格数
+        PdfPTable twoTable2 = new PdfPTable(name2.length);
+        twoTable2.setWidthPercentage(widthPercentage);
+        twoTable2.setTotalWidth(floats5);
+        //循环将表头数据添加到第二行表格中
+        for (int i = 0; i < name2.length; i++) {
+            PdfPCell pdfPCell = ItextPdfUtils.pdfTableStyle6(name2[i], size13font, 35, true, true);
+            twoTable2.addCell(pdfPCell);
+        }
+        document.add(twoTable2);
+        //将数据放入表格中
+        for (int i = 0; i < users.size(); i++) {
+            User user = users.get(i);
+            PdfPTable dataTable = new PdfPTable(4);
+            dataTable.setWidths(floats5);
+            dataTable.setWidthPercentage(80);
+            dataTable.addCell(ItextPdfUtils.pdfTableStyle6(user.getName(), size13font, 50, true, true));
+            dataTable.addCell(ItextPdfUtils.pdfTableStyle6(user.getCompanyName(), size13font, 50, true, true));
+            dataTable.addCell(ItextPdfUtils.pdfTableStyle6(user.getPosition(), size13font, 50, true, true));
+            dataTable.addCell(ItextPdfUtils.pdfTableStyle6(user.getName()+user.getPhone().substring(0,3), sigFont, 50, true, true));
+            document.add(dataTable);
+        }
+        document.close();
+        writer.close();
+        BladeFile bladeFile = newIOSSClient.uploadFile("file.pdf", localFile);
+        if (bladeFile == null || StringUtils.isBlank(bladeFile.getLink())){
+            throw new ServiceException("文件上传失败");
+        }
+        return bladeFile.getLink();
+    }
+
     @Override
     public Boolean checkSubmit(Long projectId) {
         //判断当前用户职位是否为专家组长,专家组长允许提交

+ 38 - 3
blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchiveExpertScoreServiceImpl.java

@@ -46,11 +46,46 @@ public class ArchiveExpertScoreServiceImpl extends BaseServiceImpl<ArchiveExpert
     public void saveBaseScoreInfo(Long projectId,Long conclusionId) {
         List<ArchiveExpertScore> list = new ArrayList<>();
         //业主
-        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"业主评分项1",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"施工准备文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"工地试验室资质证书、延期文件、仪器标定证书",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"会议纪要、往来文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"桥隧工程风险评估报告",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"质评资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"进度进化控制文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"计量支付文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"工程变更令",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"总结",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,1,"照片",10,0,10,0));
         //监理
-        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"监理评分项1",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"监理机构、制度",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"会议纪要、往来文件、监理费用、支付报表、监理日志、总结",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"工地试验室资质证书、延期文件、仪器标定证书",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"试验资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"质评资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"安全资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"监理指令及回复、旁站记录、巡视记录",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,2,"照片",10,0,10,0));
         //施工
-        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"施工评分项1",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"设计变更及竣工图",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"施工准备文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"试验资料(含工地试验室资质证书、仪器标定证书等)",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"路基工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"路面工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"隧道工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"绿化工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"交通与安全工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"机电工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"房建工程质检资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"质评资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"进度进化控制文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"安全生产、文明施工资料",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"施工日志、大事记",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"计量支付文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"会议纪要、往来文件",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"照片",10,0,10,0));
+        list.add(new ArchiveExpertScore(projectId,conclusionId,3,"总结",10,0,10,0));
         this.saveBatch(list);
     }
 

+ 230 - 0
blade-service/blade-archive/src/main/java/org/springblade/archive/utils/ItextPdfUtils.java

@@ -0,0 +1,230 @@
+package org.springblade.archive.utils;
+
+import com.itextpdf.text.*;
+import com.itextpdf.text.pdf.PdfPCell;
+import com.itextpdf.text.pdf.PdfPTable;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+/**
+ * @Param
+ * @Author wangwl
+ * @Date 2024/1/18 10:23
+ **/
+public class ItextPdfUtils {
+    //表格高度
+    private static int high = 20;
+    //表格宽度
+    private static int widthPercentage = 80;
+    //开始靠左,无边框
+    public static void startLeft(Document document, Font font, String text, Integer width) throws DocumentException {
+        PdfPTable twoTable = new PdfPTable(1);
+        twoTable.setWidthPercentage(width);
+        Paragraph phrase = new Paragraph(text,font);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_LEFT); // 设置水平居左
+        pdfPCell.disableBorderSide(15);
+        twoTable.addCell(pdfPCell);
+        document.add(twoTable);
+    }
+
+    //末尾靠右,无边框
+    public static void endRight(Document document,Font font,String text,Integer width) throws DocumentException {
+        PdfPTable twoTable = new PdfPTable(1);
+        twoTable.setWidthPercentage(width);
+        Chunk chunk = new Chunk(text,font);
+        //设置行间距
+        chunk.setLineHeight(20);
+        Paragraph phrase = new Paragraph(0,chunk);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_RIGHT); // 设置水平居右
+        pdfPCell.disableBorderSide(15);
+        twoTable.addCell(pdfPCell);
+        document.add(twoTable);
+    }
+    //文本,每页占满,并且分隔换行
+    public static void tableText(Document document,Font size10font,String text) throws DocumentException {
+        PdfPTable twoTable = new PdfPTable(1);
+        twoTable.setWidthPercentage(widthPercentage);
+        //设置每页占满
+        twoTable.setSplitLate(false);
+        String[] split = text.split("\n");
+        for (String s : split) {
+            PdfPCell cell = pdfTableStyle2(s, size10font);
+            twoTable.addCell(cell);
+        }
+        document.add(twoTable);
+    }
+
+
+    //标题使用,居中无边框
+    public static void tableHeader(Document document,Font size17font,String title) throws DocumentException {
+        //创建第一行
+        PdfPTable tableName = new PdfPTable(1);
+        tableName.setWidthPercentage(widthPercentage);  //设置标题长度占纸张比例
+        PdfPCell cell = pdfTableStyle(title, size17font,high);
+        //给表格赋值
+        tableName.addCell(cell);
+        //将表格添加到文档对象中
+        document.add(tableName);
+    }
+
+    //单列小标题,无边框,靠左
+    public static void rowHeader(Document document,String context,Font font,int width,int high) throws DocumentException {
+        //创建小标题
+        PdfPTable tableName = new PdfPTable(1);
+        //为小标题设置宽度来做成首行缩进
+        tableName.setWidthPercentage(width);
+        PdfPCell cell = pdfTableStyle3(context, font,  false, true);
+        cell.setMinimumHeight(high);
+        cell.disableBorderSide(15);
+        //给表格赋值
+        tableName.addCell(cell);
+        //将表格添加到文档对象中
+        document.add(tableName);
+    }
+    //小标题,居中,有边框
+    public static void tableUnit(Document document,Font font,String unitName,int high) throws DocumentException {
+        //单位名称
+        PdfPTable two = new PdfPTable(1);
+        two.setWidthPercentage(widthPercentage);
+        PdfPCell cell2 = pdfTableStyle4(unitName, font,high);
+        two.addCell(cell2);
+        document.add(two);
+    }
+
+    //空白行
+    public static void blankRow(Document document,Font size14font,int high) throws DocumentException {
+        PdfPTable tableName = new PdfPTable(1);
+        tableName.setWidthPercentage(widthPercentage);  //设置标题长度占纸张比例
+        PdfPCell cell3 = pdfTableStyle("", size14font, high);
+        cell3.disableBorderSide(15);
+        //给表格赋值
+        tableName.addCell(cell3);
+        //将表格添加到文档对象中
+        document.add(tableName);
+    }
+
+
+    //带边框线,水平垂直居中的小标题
+    public static PdfPCell pdfTableStyle7(String content, Font font,int high) {
+        Paragraph phrase = new Paragraph(content,font);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.setMinimumHeight(high);
+        pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER); // 设置水平居中
+        pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE); // 设置垂直居中
+        return pdfPCell;
+    }
+    //标题用的字体风格
+    public static PdfPCell pdfTableStyle(String content, Font font,int high) {
+        Paragraph phrase = new Paragraph(content,font);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.setMinimumHeight(high);
+        pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER); // 设置当前行水平居中
+        pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE); // 设置垂直居中
+        pdfPCell.disableBorderSide(15);
+        return pdfPCell;
+    }
+
+    // 设置文本字体
+    public static PdfPCell pdfTableStyle2(String content, Font font) {
+        Chunk chunk = new Chunk("    "+content);
+        chunk.setFont(font);
+        //设置行间距
+        chunk.setLineHeight(20);
+        //每个字符间距
+        Paragraph phrase = new Paragraph(0,chunk);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.disableBorderSide(15);
+        pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_LEFT); // 设置当前行水平居左
+        pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE); // 设置垂直居中
+        return pdfPCell;
+    }
+
+    // 设置小标题字体
+    public static PdfPCell pdfTableStyle3(String content, Font font,boolean isAlignCenter, boolean isAlignMidle) {
+        Chunk chunk = new Chunk("     "+content);
+        chunk.setFont(font);
+        //设置行间距
+        chunk.setLineHeight(20);
+        //每个字符间距
+//        chunk.setCharacterSpacing(4);
+        Paragraph phrase = new Paragraph(0,chunk);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        if (isAlignCenter) {
+            pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER); // 设置水平居中
+        }else {
+            pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_LEFT); // 设置水平居中
+        }
+        if (isAlignMidle) {
+            pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE); // 设置垂直居中
+        }else {
+            pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_LEFT); // 设置垂直居中
+        }
+
+        return pdfPCell;
+    }
+
+
+    //单位格式
+    public static PdfPCell pdfTableStyle4(String content, Font font,int high)  {
+        Paragraph phrase = new Paragraph(content, font);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.setMinimumHeight(high);
+        pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER); // 设置当前行水平居左
+        pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE); // 设置垂直居中
+        return pdfPCell;
+    }
+
+    public static PdfPCell pdfTableStyle6(String content, Font font, int high, boolean isAlignCenter, boolean isAlignMidle) {
+        Paragraph phrase = new Paragraph(content, font);
+        PdfPCell pdfPCell = new PdfPCell(phrase);
+        pdfPCell.setMinimumHeight(high);
+        pdfPCell.setUseAscender(true); // 设置可以居中
+        pdfPCell.setBorderWidth(0.5F);
+        if (isAlignCenter) {
+            pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_CENTER); // 设置水平居中
+        }else {
+            pdfPCell.setHorizontalAlignment(PdfPCell.ALIGN_LEFT); // 设置水平居中
+        }
+        if (isAlignMidle) {
+            pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_MIDDLE); // 设置垂直居中
+        }else {
+            pdfPCell.setVerticalAlignment(PdfPCell.ALIGN_LEFT); // 设置垂直居中
+        }
+        return pdfPCell;
+    }
+
+    public static void rowHeader2(Document document,String context,Font font,String sigCode,Font sigFont) throws DocumentException {
+        //做左右分隔
+        float[] floats = new float[3];
+        floats[0] = 0.15f;
+        floats[1] = 0.6f;
+        floats[2] = 0.2f;
+        //创建小标题
+        PdfPTable tableName = new PdfPTable(3);
+        tableName.setTotalWidth(floats);
+        tableName.setWidthPercentage(widthPercentage);  //设置标题长度占纸张比例
+        Paragraph phrase1 = new Paragraph(context,font);
+        phrase1.setAlignment(PdfPCell.ALIGN_LEFT);
+        //签名
+        Paragraph phrase2 = new Paragraph(sigCode,sigFont);
+        phrase2.setAlignment(PdfPCell.ALIGN_LEFT);
+        Paragraph phrase3 = new Paragraph(new SimpleDateFormat("yyyy年M月dd日  ").format(new Date()).toString(), font);
+        phrase3.setAlignment(PdfPCell.ALIGN_RIGHT);
+        PdfPCell cell1 = new PdfPCell(phrase1);
+        cell1.disableBorderSide(15);
+        PdfPCell cell2 = new PdfPCell(phrase2);
+        cell2.disableBorderSide(15);
+        PdfPCell cell3 = new PdfPCell(phrase3);
+        cell3.disableBorderSide(15);
+        //给表格赋值
+        tableName.addCell(cell1);
+        tableName.addCell(cell2);
+        tableName.addCell(cell3);
+        //将表格添加到文档对象中
+        document.add(tableName);
+    }
+
+}

+ 128 - 0
blade-service/blade-archive/src/main/java/org/springblade/archive/utils/MyPdfPageHelper.java

@@ -0,0 +1,128 @@
+package org.springblade.archive.utils;
+
+import com.itextpdf.text.*;
+import com.itextpdf.text.pdf.*;
+
+import java.io.IOException;
+
+/**
+ * @Param   itext生成页脚
+ * @Author wangwl
+ * @Date 2024/1/17 16:31
+ **/
+public class MyPdfPageHelper extends PdfPageEventHelper {
+    /**
+     * 页眉
+     */
+    public String header = "";
+    /**
+     * 文档字体大小,页脚页眉最好和文本大小一致
+     */
+    public int presentFontSize = 12;
+    /**
+     * 文档页面大小,最好前面传入,否则默认为A4纸张
+     */
+    public Rectangle pageSize = PageSize.A4;
+    // 模板
+    public PdfTemplate total = null;
+    // 基础字体对象
+    public BaseFont bf = null;
+    // 利用基础字体生成的字体对象,一般用于生成中文文字
+    public Font fontDetail = null;
+
+    public MyPdfPageHelper() {
+
+    }
+
+    /**
+     * @param yeMei
+     *            页眉字符串
+     * @param presentFontSize
+     *            数据体字体大小
+     * @param pageSize
+     *            页面文档大小,A4,A5,A6横转翻转等Rectangle对象
+     */
+    public MyPdfPageHelper(String yeMei, int presentFontSize, Rectangle pageSize) {
+        this.header = yeMei;
+        this.presentFontSize = presentFontSize;
+        this.pageSize = pageSize;
+    }
+
+    public void setHeader(String header) {
+        this.header = header;
+    }
+
+    public void setPresentFontSize(int presentFontSize) {
+        this.presentFontSize = presentFontSize;
+    }
+
+    /**
+     * TODO 文档打开时创建模板
+     */
+    @Override
+    public void onOpenDocument(PdfWriter writer, Document document) {
+        total = writer.getDirectContent().createTemplate(50, 50);// 共页的矩形的长宽高
+    }
+
+    /**
+     * TODO 关闭每页的时候,写入页眉,写入'第几页共'这几个字。
+     */
+    @Override
+    public void onEndPage(PdfWriter writer, Document document) {
+        try {
+            if (bf == null) {
+                bf = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED);
+            }
+            if (fontDetail == null) {
+                fontDetail = new Font(bf, presentFontSize, Font.NORMAL);// 数据体字体
+            }
+        } catch (DocumentException e) {
+            e.printStackTrace();
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+
+        // 拿到当前的PdfContentByte
+        PdfContentByte cb = writer.getDirectContent();
+
+        // 1.写入页眉     参数:要写入文本的页面对象,对齐,文字内容,X轴位置,Y轴位置,逆时针旋转的角度
+        ColumnText.showTextAligned(cb, Element.ALIGN_LEFT, new Phrase(header, fontDetail), document.left(), document.top() + 20, 45);
+
+        // 2.写入页脚    前半部分的 第 X页/共
+        int pageS = writer.getPageNumber();
+        String foot1 = "第 " + pageS + " 页";
+        Phrase footer = new Phrase(foot1, fontDetail);
+
+        // 计算前半部分的foot1的长度,后面好定位最后一部分的'Y页'这俩字的x轴坐标,字体长度也要计算进去 = len
+        float len = bf.getWidthPoint(foot1, presentFontSize);
+
+        /**
+         *  写入页脚   前半部分的    第 X页/共
+         * x轴就是(右margin+左margin + right() -left()- len)/2.0F 再给偏移20F适合人类视觉感受,否则肉眼看上去就太偏左了
+         * y轴就是底边界-20,否则就贴边重叠到数据体里了就不是页脚了;注意Y轴是从下往上累加的,最上方的Top值是大于Bottom好几百开外的。
+         */
+        ColumnText.showTextAligned(cb, Element.ALIGN_CENTER, footer, (document.rightMargin() + document.right() + document.leftMargin() - document.left() - len) / 2.0F + 20F, document.bottom() - 20, 0);
+
+        /**
+         *  写入页脚  后半部分   ?页
+         *  注:因为共?页   中的?值是在doc.close() 后才能得到,所以这一先加入模板,最后结束的时候后边用值替换
+         * x=(右margin+左margin + right() -left())/2.0F
+         * y 轴和之前的保持一致,底边界-20
+         */
+//        cb.addTemplate(total, (document.rightMargin() + document.right() + document.leftMargin() - document.left()) / 2.0F + 20F, document.bottom() - 20); // 调节模版显示的位置
+    }
+
+    /**
+     * TODO 关闭文档时,替换模板,完成整个页眉页脚组件
+     */
+    @Override
+    public void onCloseDocument(PdfWriter writer, Document document) {
+        // 7.最后一步了,就是关闭文档的时候,将模板替换成实际的 Y 值,至此,page x of y 制作完毕,完美兼容各种文档size。
+        total.beginText();
+        total.setFontAndSize(bf, presentFontSize);// 生成的模版的字体、颜色
+        String foot2 = " " + writer.getPageNumber() + " 页";
+        total.showText(foot2);// 模版显示的内容
+        total.endText();
+        total.closePath();
+    }
+}

+ 16 - 1
blade-service/blade-business/src/main/java/org/springblade/business/controller/TaskController.java

@@ -655,6 +655,8 @@ public class TaskController extends BladeController {
                                 //都是完成状态,则修改主任务的状态
                                 task.setStatus(2);
                                 taskService.updateById(task);
+                                //专家账号id集合
+                                StringBuilder expertIds = new StringBuilder();
                                 //保存专家账号
                                 String formDataId = task.getFormDataId();
                                 List<SaveApplyDTO.ExpertInfo> expertInfoList = JSON.parseArray(formDataId, SaveApplyDTO.ExpertInfo.class);
@@ -667,6 +669,11 @@ public class TaskController extends BladeController {
                                     //如果当前账户已经存在,则代表账号已经注册,直接跳过当前
                                     R<User> r = userClient.userByAccount(AuthUtil.getTenantId(), dto.getAccount());
                                     if (r.getData() != null) {
+                                        if (expertIds.length() == 0){
+                                            expertIds.append(r.getData().getId());
+                                        }else {
+                                            expertIds.append(","+r.getData().getId());
+                                        }
                                         continue;
                                     }
                                     StringSPUtils stringSPUtils = new StringSPUtils();
@@ -690,11 +697,19 @@ public class TaskController extends BladeController {
                                     }
                                     list.add(projectDTO);
                                     dto.setProjectAndUserList(list);
+                                    //设置id
+                                    Long id = SnowFlakeUtil.getId();
+                                    dto.setId(id);
                                     //单个保存专家信息
                                     R<Boolean> booleanR = userClient.saveUserDTO(dto);
                                     if (booleanR.getData() == null || !booleanR.isSuccess()) {
                                         throw new ServiceException(booleanR.getMsg());
                                     }
+                                    if (expertIds.length() == 0){
+                                        expertIds.append(id);
+                                    }else {
+                                        expertIds.append(","+id);
+                                    }
                                 }
                                 //修改档案类型
                                 String archiveIds = task.getArchiveIds();
@@ -706,7 +721,7 @@ public class TaskController extends BladeController {
                                     }
                                 }
                                 //创建报表基本信息,报表中会自动创建评分基础信息
-                                R r = conclusionClient.saveBaseTableInfo(Long.parseLong(task.getProjectId()), task.getAttachmentPdfUrl(),task.getId());
+                                R r = conclusionClient.saveBaseTableInfo(Long.parseLong(task.getProjectId()), task.getAttachmentPdfUrl(),task.getId(),expertIds.toString());
                                 if (r == null ){
                                     throw new ServiceException("调用档案服务失败");
                                 }