소스 검색

Merge branch 'refs/heads/dev' into feature-lihb-20250806

# Conflicts:
#	blade-service/blade-business/src/main/java/org/springblade/business/service/impl/TaskServiceImpl.java
LHB 1 개월 전
부모
커밋
c78baf7de0
100개의 변경된 파일3987개의 추가작업 그리고 197개의 파일을 삭제
  1. 7 2
      blade-common/src/main/java/org/springblade/common/utils/YiKeYunApiUtils.java
  2. 0 1
      blade-gateway/src/main/java/org/springblade/gateway/provider/AuthProvider.java
  3. 2 2
      blade-ops/blade-resource/src/main/java/org/springblade/resource/builder/oss/OssBuilder.java
  4. 17 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/FindAndReplaceDto1.java
  5. 35 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/RecycleBinInfoDTO.java
  6. 20 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/StartTimeAndEndTime.java
  7. 53 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialClassificationTreeDTO.java
  8. 11 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialClassificationTreeDTO1.java
  9. 3 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialFileSubmitDTO.java
  10. 3 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialSelfInspectionRecordPageDTO.java
  11. 85 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialSystemDockingDTO.java
  12. 48 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialSystemDockingDTO1.java
  13. 12 1
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/ArchiveFile.java
  14. 97 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/ContractLogMonthPack.java
  15. 7 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/InformationQuery.java
  16. 135 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/RecycleBinInfo.java
  17. 69 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialClassificationTree.java
  18. 59 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyAccessories.java
  19. 149 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyFinishTestReport.java
  20. 54 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyTestType.java
  21. 285 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyThirdReport.java
  22. 106 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialSystemDocking.java
  23. 14 7
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/WbsTreeContractStatistics.java
  24. 8 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/feign/ArchiveFileClient.java
  25. 24 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/feign/TrialCyAccessoriesClient.java
  26. 3 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/feign/WbsTreeContractStatisticsClient.java
  27. 45 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/ChekPdfPaceVo.java
  28. 9 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/ContractLogVO.java
  29. 3 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/EntrustInfoVO.java
  30. 13 3
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/InformationQueryVO.java
  31. 64 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/NeiYeLedgerVO.java
  32. 9 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/NeiYeQueryVO.java
  33. 36 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/QueryProcessDataVO.java
  34. 72 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/RecycleBinInfoVO.java
  35. 13 3
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TaskApprovalVO.java
  36. 20 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/ThirdReportVo.java
  37. 50 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TrialClassificationTreeVO.java
  38. 32 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TrialCyThirdReportQueryVo.java
  39. 84 0
      blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TrialSystemDockingVO.java
  40. 4 1
      blade-service-api/blade-e-visa-api/src/main/java/org/springblade/evisa/vo/SealStrategyVO.java
  41. 50 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/dto/BatchAddNumbersDTO.java
  42. 11 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/dto/MoveNodeDTO.java
  43. 4 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/Album.java
  44. 36 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/AlbumImages.java
  45. 5 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/ProjectInfo.java
  46. 7 4
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/TableFile.java
  47. 67 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/WbsTreeContractExtend.java
  48. 61 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/WbsTreeContractOldHtml.java
  49. 2 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/WbsTreePrivate.java
  50. 18 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/INodeBaseInfoServiceClient.java
  51. 5 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsParamClient.java
  52. 7 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsTreeContractClient.java
  53. 25 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsTreeContractOldHtmlClient.java
  54. 84 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/APIWbsContractSubdivisionVo.java
  55. 2 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/AppWbsTreeContractVO.java
  56. 2 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/ExceTabTreVO.java
  57. 2 1
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/WbsTreeContractLazyVO.java
  58. 6 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/WbsTreeContractTreeAllVO.java
  59. 8 0
      blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/WbsTreePrivateVO.java
  60. 27 8
      blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchiveFileController.java
  61. 8 2
      blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchivesAutoController.java
  62. 1 1
      blade-service/blade-archive/src/main/java/org/springblade/archive/mapper/ArchivesAutoMapper.java
  63. 4 0
      blade-service/blade-archive/src/main/java/org/springblade/archive/mapper/ArchivesAutoMapper.xml
  64. 12 2
      blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchiveAutoPdfServiceImpl.java
  65. 36 30
      blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchivesAutoServiceImpl.java
  66. 1 0
      blade-service/blade-business/pom.xml
  67. 42 0
      blade-service/blade-business/src/main/java/org/springblade/business/controller/ContractLogController.java
  68. 182 76
      blade-service/blade-business/src/main/java/org/springblade/business/controller/InformationWriteQueryController.java
  69. 11 4
      blade-service/blade-business/src/main/java/org/springblade/business/controller/MaterialProgressController.java
  70. 2 2
      blade-service/blade-business/src/main/java/org/springblade/business/controller/NeiWaiYeProgressController.java
  71. 94 10
      blade-service/blade-business/src/main/java/org/springblade/business/controller/NeiYeController.java
  72. 110 0
      blade-service/blade-business/src/main/java/org/springblade/business/controller/RecycleBinController.java
  73. 29 6
      blade-service/blade-business/src/main/java/org/springblade/business/controller/TaskController.java
  74. 207 0
      blade-service/blade-business/src/main/java/org/springblade/business/controller/TrialClassificationTreeController.java
  75. 100 0
      blade-service/blade-business/src/main/java/org/springblade/business/controller/TrialCyController.java
  76. 166 0
      blade-service/blade-business/src/main/java/org/springblade/business/controller/TrialSystemDockingController.java
  77. 103 0
      blade-service/blade-business/src/main/java/org/springblade/business/feignClient/ArchiveFileClientImpl.java
  78. 118 0
      blade-service/blade-business/src/main/java/org/springblade/business/feignClient/TrialCyAccessoriesClientImpl.java
  79. 15 5
      blade-service/blade-business/src/main/java/org/springblade/business/feignClient/WbsTreeContractStatisticsClientImpl.java
  80. 2 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/ArchiveFileMapper.java
  81. 9 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/ArchiveFileMapper.xml
  82. 18 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/ContractLogMonthPackMapper.java
  83. 28 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/ContractLogMonthPackMapper.xml
  84. 3 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/EntrustInfoMapper.xml
  85. 1 1
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/ImageClassificationFileMapper.xml
  86. 9 2
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/InformationQueryMapper.java
  87. 54 22
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/InformationQueryMapper.xml
  88. 17 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/RecycleBinInfoMapper.java
  89. 95 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/RecycleBinInfoMapper.xml
  90. 50 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialClassificationTreeMapper.java
  91. 45 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialClassificationTreeMapper.xml
  92. 27 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyAccessoriesMapper.java
  93. 28 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyAccessoriesMapper.xml
  94. 23 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyFinishTestReportMapper.java
  95. 37 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyFinishTestReportMapper.xml
  96. 23 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyTestTypeMapper.java
  97. 24 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyTestTypeMapper.xml
  98. 24 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyThirdReportMapper.java
  99. 36 0
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyThirdReportMapper.xml
  100. 4 1
      blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialSelfInspectionRecordMapper.java

+ 7 - 2
blade-common/src/main/java/org/springblade/common/utils/YiKeYunApiUtils.java

@@ -100,8 +100,13 @@ public class YiKeYunApiUtils {
      * @param cityId
      * @return
      */
-    public static Map<String, Map<String, String>> getHistoryWeather(String cityId, Integer year, Integer month) {
-        String getUrl = String.format("http://gfeljm.tianqiapi.com/free/history?appid=%s&appsecret=%s&cityid=%s&year=%d&month=%d", API_YIKEYUN_APPID, API_YIKEYUN_APPSECRET, cityId, year, month);
+    public static Map<String, Map<String, String>> getHistoryWeather(String cityId, Integer year, Integer month, String date1) {
+        String getUrl;
+        if (date1 != null && date1.matches("\\d{4}-\\d{2}-\\d{2}")) {
+            getUrl = String.format("http://gfeljm.tianqiapi.com/free/history?appid=%s&appsecret=%s&cityid=%s&date=%s", API_YIKEYUN_APPID, API_YIKEYUN_APPSECRET, cityId, date1);
+        } else {
+            getUrl = String.format("http://gfeljm.tianqiapi.com/free/history?appid=%s&appsecret=%s&cityid=%s&year=%d&month=%d", API_YIKEYUN_APPID, API_YIKEYUN_APPSECRET, cityId, year, month);
+        }
         Map<String, Map<String, String>> map = new HashMap<>();
         try {
             URL url = new URL(getUrl);

+ 0 - 1
blade-gateway/src/main/java/org/springblade/gateway/provider/AuthProvider.java

@@ -66,7 +66,6 @@ public class AuthProvider {
         DEFAULT_SKIP_URL.add("/getPk"); //成渝第三方登录获取公钥
         DEFAULT_SKIP_URL.add("/getQualityTestingToken"); //成渝第三方登录获取质检系统tokne
         DEFAULT_SKIP_URL.add("/getArchiveToken"); //成渝第三方登录获取档案系统tokne
-
     }
 
     /**

+ 2 - 2
blade-ops/blade-resource/src/main/java/org/springblade/resource/builder/oss/OssBuilder.java

@@ -91,13 +91,13 @@ public class OssBuilder {
 		String tenantId = AuthUtil.getTenantId();
 		Oss oss = getOss(tenantId, code);
         String sys_isonline = ParamCache.getValue(CommonConstant.SYS_ISONLINE);
-        if(SystemUtils.isMacOs()||SystemUtils.isWindows()){
+       /* if(SystemUtils.isMacOs()||SystemUtils.isWindows()){
             if("20".equals(sys_isonline)){
                 oss.setEndpoint("http://183.247.216.148:9000/");
             }else {
                 oss.setEndpoint("https://xinan1.zos.ctyun.cn");
             }
-        }
+        }*/
 		//oss.setEndpoint("https://xinan1.zos.ctyun.cn");
 		System.out.println("oss111="+oss.getEndpoint());
 		Oss ossCached = ossPool.get(tenantId);

+ 17 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/FindAndReplaceDto1.java

@@ -0,0 +1,17 @@
+package org.springblade.business.dto;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+import org.springblade.archive.dto.FindAndReplaceDto;
+import org.springblade.business.entity.ArchiveFile;
+
+import java.util.List;
+
+@Data
+@NoArgsConstructor
+@AllArgsConstructor
+public class FindAndReplaceDto1 {
+    private FindAndReplaceDto dto;
+    private List<ArchiveFile> list;
+}

+ 35 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/RecycleBinInfoDTO.java

@@ -0,0 +1,35 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.dto;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+
+
+@Data
+public class RecycleBinInfoDTO implements Serializable {
+    private static final long serialVersionUID = 1L;
+
+    @ApiModelProperty("ids")
+    private String ids;
+
+    @ApiModelProperty("是否恢复同批次全部删除数据, 0否,1是")
+    private Integer recoverOperationData;
+
+}

+ 20 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/StartTimeAndEndTime.java

@@ -0,0 +1,20 @@
+package org.springblade.business.dto;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.NotNull;
+
+/**
+ * @author LHB
+ */
+@Data
+public class StartTimeAndEndTime {
+    @ApiModelProperty("开始时间")
+    @NotBlank(message = "开始时间不能为空")
+    private String startTime;
+    @ApiModelProperty("结束时间")
+    @NotBlank(message = "结束时间不能为空")
+    private String endTime;
+}

+ 53 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialClassificationTreeDTO.java

@@ -0,0 +1,53 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.dto;
+
+import org.springblade.business.entity.TrialClassificationTree;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 德飞试验系统检测分类树数据传输对象实体类
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@Data
+public class TrialClassificationTreeDTO {
+	private static final long serialVersionUID = 1L;
+
+
+	private Long id;
+
+	/**
+	 * 父级ID
+	 */
+	private Long parentId;
+
+	/**
+	 * 项目ID
+	 */
+
+	private Long projectId;
+
+	/**
+	 * 分类名称
+	 */
+	private String classificationName;
+
+
+}

+ 11 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialClassificationTreeDTO1.java

@@ -0,0 +1,11 @@
+package org.springblade.business.dto;
+
+import lombok.Data;
+
+import java.util.List;
+
+@Data
+public class TrialClassificationTreeDTO1 {
+   private List<TrialClassificationTreeDTO> list;
+   private Integer groupType;
+}

+ 3 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialFileSubmitDTO.java

@@ -24,4 +24,7 @@ public class TrialFileSubmitDTO implements Serializable {
     @ApiModelProperty(value = "合同段id")
     private String contractId;
 
+    @ApiModelProperty(value = "附件类型(table_file_type 字典数据)")
+    private String tableFileType;
+
 }

+ 3 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialSelfInspectionRecordPageDTO.java

@@ -27,4 +27,7 @@ public class TrialSelfInspectionRecordPageDTO extends TrialSelfInspectionRecord
 
     @ApiModelProperty(value = "排序类型, 1 记录/报告编号升序, 2 记录/报告编号降序, 3 规格型号升序, 4 规格型号降序")
     private String sortType;
+
+    @ApiModelProperty("类型:0-施工,1-监理,2-业主")
+    private Integer reportType;
 }

+ 85 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialSystemDockingDTO.java

@@ -0,0 +1,85 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.dto;
+
+import org.springblade.business.entity.TrialSystemDocking;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+import javax.validation.constraints.NotNull;
+
+/**
+ * 德飞试验系统对接表数据传输对象实体类
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@Data
+public class TrialSystemDockingDTO {
+	private static final long serialVersionUID = 1L;
+
+	/**
+	 * 德飞数据ID
+	 */
+	private Long dataId;
+
+	/**
+	 * 项目Id
+	 */
+	@NotNull(message = "projectId 不能为空")
+	private Long projectId;
+	/**
+	 * 报告文件名称
+	 */
+	private String reportName;
+	/**
+	 * 报告编号
+	 */
+	private String reportNumber;
+	/**
+	 * 单位名称
+	 */
+	private String unitName;
+	/**
+	 * 所属检测分类id
+	 */
+	@NotNull(message = "projectId 不能为空")
+	private Long classificationId;
+	/**
+	 * 规格型号
+	 */
+	private String specification;
+	/**
+	 * 报告类型(1原材检测报告,2现场检测报告,3外委报告,4第三方检测报告)
+	 */
+	private Integer reportType;
+	/**
+	 * 工程用途及部位
+	 */
+	private String purposeLocation;
+	/**
+	 * 报告日期(20250822)
+	 */
+	private String reportDate;
+	/**
+	 * 原文件地址
+	 */
+	private String fileUrl;
+
+	private String personInCharge;
+
+}

+ 48 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/dto/TrialSystemDockingDTO1.java

@@ -0,0 +1,48 @@
+package org.springblade.business.dto;
+
+import lombok.Data;
+
+import javax.validation.constraints.NotNull;
+
+@Data
+public class TrialSystemDockingDTO1 {
+    private static final long serialVersionUID = 1L;
+    /**
+     * 主键
+     */
+    private Long id;
+    /**
+     * 报告文件名称
+     */
+    private String reportName;
+    /**
+     * 报告编号
+     */
+    private String reportNumber;
+    /**
+     * 单位名称
+     */
+    private String unitName;
+    /**
+     * 规格型号
+     */
+    private String specification;
+    /**
+     * 报告类型(1原材检测报告,2现场检测报告,3外委报告,4第三方检测报告)
+     */
+    private Integer reportType;
+    /**
+     * 工程用途及部位
+     */
+    private String purposeLocation;
+    /**
+     * 报告日期(20250822)
+     */
+    private String reportDate;
+    /**
+     * 原文件地址
+     */
+    private String fileUrl;
+
+    private String personInCharge;
+}

+ 12 - 1
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/ArchiveFile.java

@@ -304,6 +304,11 @@ public class ArchiveFile extends BaseEntity {
      */
     @ApiModelProperty("u_image_classification_file_id表中的主键id")
     private Long uImageClassificationFileId;
+    /**
+     * m_album表中的主键id
+     */
+    @ApiModelProperty("u_image_classification_file_id表中的主键id")
+    private Long mAlbumId;
 
     /**
      * 归档文件储存类型,可看代码枚举
@@ -331,6 +336,8 @@ public class ArchiveFile extends BaseEntity {
     private String outId;
 
     private String sortNum;
+
+    private String remark;
     @ApiModelProperty("是否锁定 1已锁定")
     private Integer isLock;
 
@@ -448,6 +455,10 @@ public class ArchiveFile extends BaseEntity {
             this.fileTime = "";
             return;
         }
-        this.fileTime = fileTime.replaceAll("[^0-9]", "");
+        if (fileTime.contains("~")) {
+            this.fileTime = fileTime;
+        } else {
+            this.fileTime = fileTime.replaceAll("[^0-9]", "");
+        }
     }
 }

+ 97 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/ContractLogMonthPack.java

@@ -0,0 +1,97 @@
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.util.Date;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * 日志按月封装表
+ * @TableName u_contract_log_month_pack
+ */
+@TableName(value ="u_contract_log_month_pack")
+@Data
+public class ContractLogMonthPack {
+    /**
+     * 
+     */
+    @TableId
+    @ApiModelProperty("id")
+    private Long id;
+
+    /**
+     * 项目id
+     */
+    @ApiModelProperty("项目id")
+    private Long projectId;
+
+    /**
+     * 合同段id
+     */
+    @ApiModelProperty("合同段id")
+    private Long contractId;
+
+    /**
+     * 私有WBS树p_key_id
+     */
+    @ApiModelProperty("私有WBS树p_key_id")
+    private Long wbsNodeId;
+
+    /**
+     *  日志类型
+     */
+    @ApiModelProperty("日志类型")
+    private Integer wbsNodeType;
+
+    /**
+     * 文件名称
+     */
+    @ApiModelProperty("文件名称")
+    private String fileName;
+
+    /**
+     * 上当月中最后一份文件的日期
+     */
+    @ApiModelProperty("上当月中最后一份文件的日期")
+    private String recordTime;
+
+    /**
+     * 合同段名称
+     */
+    @ApiModelProperty("合同段名称(责任者)")
+    private String contractName;
+
+    /**
+     *  页数
+     */
+    @ApiModelProperty("页数")
+    private Integer page;
+
+    /**
+     * pdf路径
+     */
+    @ApiModelProperty("pdf路径")
+    private String pdfUrl;
+
+    /**
+     *  创建时间
+     */
+    private Date createTime;
+
+    /**
+     *  创建人
+     */
+    private Long createUser;
+
+    /**
+     *  修改时间
+     */
+    private Date updateTime;
+
+    /**
+     *  修改人
+     */
+    private Long updateUser;
+}

+ 7 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/InformationQuery.java

@@ -143,4 +143,11 @@ public class InformationQuery extends BaseEntity {
 
     @ApiModelProperty("重刷次数:如果次数大于5次 每次都是3,就停止重刷")
     private Integer saveAgainCount;
+
+    @ApiModelProperty("0-未检出,1-已提交,2-检查无误,3-检查有误")
+    private Integer chekStatus;
+
+    @ApiModelProperty("检查描述")
+    private String checkDesc;
+
 }

+ 135 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/RecycleBinInfo.java

@@ -0,0 +1,135 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.springblade.core.mp.base.BaseEntity;
+import org.springblade.core.secure.utils.AuthUtil;
+import org.springblade.core.tool.utils.DateUtil;
+
+import java.util.Date;
+
+/**
+ * 实体类
+ *
+ * @author BladeX
+ * @since 2022-07-19
+ */
+@Data
+@TableName("u_recycle_bin_info")
+@EqualsAndHashCode(callSuper = true)
+public class RecycleBinInfo extends BaseEntity {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 项目ID
+     */
+    @ApiModelProperty("项目ID")
+    private Long projectId;
+    /**
+     * 合同段ID
+     */
+    @ApiModelProperty("合同段ID")
+    private Long contractId;
+
+    @ApiModelProperty("删除的id")
+    private Long delId;
+
+    @ApiModelProperty("删除位置id")
+    private Long delRootId;
+
+    @ApiModelProperty("删除位置名称")
+    private String delRootName;
+
+    @ApiModelProperty("操作记录id")
+    private String operationId;
+
+    /**
+     * 删除的类型,文件资料1,工程划分2,影像资料3
+     */
+    @ApiModelProperty("删除的类型,文件资料1,工程划分2,影像资料3")
+    private Integer delType;
+
+    /**
+     * 是否是资料节点,0否,1是
+     */
+    @ApiModelProperty("是否是资料节点,0否,1是")
+    private Integer isData;
+
+    /**
+     * 文件名称
+     */
+    @ApiModelProperty("文件名称(施工)")
+    private String fileName;
+
+    @ApiModelProperty("文件名称(监理)")
+    private String jlFileName;
+
+    /**
+     * 所在位置,即节点路径
+     */
+    @ApiModelProperty("所在位置,即节点路径")
+    private String position;
+    /**
+     * 业务ID
+     */
+    @ApiModelProperty("业务ID")
+    private String businessId;
+    /**
+     * 操作时间,与创建时间相同
+     */
+    @ApiModelProperty("操作时间,与创建时间相同")
+    private String operationTime;
+
+    @ApiModelProperty("操作人姓名")
+    private String createUserName;
+
+    @ApiModelProperty("更新者姓名")
+    private String updateUserName;
+
+    @TableField(exist = false)
+    @ApiModelProperty("删除信息")
+    private String delInfo;
+
+    public RecycleBinInfo(String businessIds, String title, Integer deletedType, String position, String projectId, String contractId) {
+        this.businessId = businessIds;
+        this.fileName = title;
+        this.delType = deletedType;
+        this.position = position;
+        this.projectId = Long.parseLong(projectId);
+        this.contractId = Long.parseLong(contractId);
+
+        this.setCreateUser(AuthUtil.getUserId());
+        this.createUserName = AuthUtil.getNickName();
+        Date now = new Date();
+        this.setCreateTime(now);
+        this.operationTime = DateUtil.format(now, "yyyy-MM-dd HH:mm:ss");
+    }
+
+    public RecycleBinInfo() {
+    }
+
+    public String getDelInfo() {
+        return this.getCreateUserName() == null ? "" : this.getCreateUserName() + "\n" + (this.getCreateTime() == null ? "" : DateUtil.format(this.getCreateTime(), "yyyy-MM-dd HH:mm:ss"));
+    }
+
+}

+ 69 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialClassificationTree.java

@@ -0,0 +1,69 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.io.Serializable;
+import org.springblade.core.mp.base.BaseEntity;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 德飞试验系统检测分类树实体类
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@Data
+@TableName("u_trial_classification_tree")
+public class TrialClassificationTree extends BaseEntity {
+
+	private static final long serialVersionUID = 1L;
+
+	/**
+	* 主键
+	*/
+	private Long id;
+
+
+
+	private Long projectId;
+	/**
+	* 父级ID
+	*/
+		private Long parentId;
+	/**
+	 * 分类祖级
+	 */
+	private String classificationAncestors;
+	/**
+	* 分类名称
+	*/
+		private String classificationName;
+
+		/**
+		 * 分组类型 1是德飞厂商
+		 */
+		private Integer groupType;
+
+	/**
+	 * 是否删除
+ 	 */
+
+	private Integer isDeleted;
+
+}

+ 59 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyAccessories.java

@@ -0,0 +1,59 @@
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * 成渝-附件信息
+ * @author LHB
+ * @TableName u_trial_cy_accessories
+ */
+@TableName(value ="u_trial_cy_accessories")
+@Data
+public class TrialCyAccessories {
+    /**
+     * 主键
+     */
+    @ApiModelProperty("唯一id")
+    @TableId(type = IdType.INPUT)
+    private Long id;
+
+    /**
+     * 报告id,已签章的报告/是第三方检测报告/外委检测报告/上传报告
+     */
+    @ApiModelProperty("报告id,已签章的报告/ 是第三方检测报告/ 外委检测报告/ 上传报告")
+    private Long reportId;
+
+    /**
+     * 成渝接口返回的id
+     */
+    @ApiModelProperty("成渝接口返回的")
+    @TableField("acc_id")
+    private String accId;
+
+    /**
+     * 类型名称
+     */
+
+    @ApiModelProperty("类型名称")
+    @TableField("acc_type")
+    private String accType;
+
+    /**
+     * 文件名称
+     */
+    @ApiModelProperty("文件名称")
+    @TableField("file_name")
+    private String fileName;
+
+    /**
+     * 文件路径
+     */
+    @ApiModelProperty("文件路径")
+    @TableField("file_path")
+    private String filePath;
+}

+ 149 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyFinishTestReport.java

@@ -0,0 +1,149 @@
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+ * 已完成(已签章完成)的检测报告接受对象
+ *
+ * @author LHB
+ */
+@TableName("u_trial_cy_finish_test_report")
+@Data
+public class TrialCyFinishTestReport {
+
+    @TableId(type = IdType.INPUT)
+    @ApiModelProperty("唯一id")
+    private Long id;
+    /**
+     * 合同ID
+     */
+    @TableField("contract_id")
+    @ApiModelProperty("合同ID")
+    private Long contractId;
+    /**
+     * 任务ID
+     */
+    @ApiModelProperty("任务ID")
+    private Integer taskId;
+    /**
+     * 合同段编码
+     */
+    @ApiModelProperty("合同段编码")
+    private String contractNumber;
+    /**
+     * 单位类型
+     * 0 施工
+     * 1 监理
+     * 2 中试
+     */
+    @ApiModelProperty("单位类型 0 施工 1 监理 2 中试")
+    private Integer cs;
+    /**
+     * 记录编号
+     */
+    @ApiModelProperty("记录编号")
+    private String number;
+    /**
+     * 报告编号
+     */
+    @ApiModelProperty("报告编号")
+    private String reportNumber;
+    /**
+     * 试验项目名称
+     */
+    @ApiModelProperty("试验项目名称")
+    private String name;
+    /**
+     * 试验工序名称
+     */
+    @ApiModelProperty("试验工序名称")
+    private String processName;
+    /**
+     * 取样地点
+     */
+    @ApiModelProperty("取样地点")
+    @TableField("sampling_place")
+    private String samplingPlace;
+    /**
+     * 样品信息 同试验检测查询界面
+     */
+    @ApiModelProperty("样品信息 同试验检测查询界面")
+    @TableField("sample_info")
+    private String sampleInfo;
+    /**
+     * 类型规格 规格型号
+     */
+    @ApiModelProperty("类型规格 规格型号")
+    @TableField("specification")
+    private String specification;
+    /**
+     * 合格证上传情况 已上传、未上传
+     */
+    @ApiModelProperty("合格证上传情况 已上传、未上传")
+    @TableField("hash_gz")
+    private String hasHGZ;
+    /**
+     * 所检参数信息 同试验检测查询界面
+     */
+    @ApiModelProperty("所检参数信息 同试验检测查询界面")
+    @TableField("test_param_info")
+    private String testParamInfo;
+    /**
+     * 报告时间
+     */
+    @ApiModelProperty("报告时间")
+    private String reportDate;
+    /**
+     * 是否合格 True 合格,False不合格
+     */
+    @ApiModelProperty("是否合格 1 合格,0 不合格")
+    private String experimentResult;
+    /**
+     * 报告人
+     */
+    @ApiModelProperty("报告人")
+    @TableField("user_name")
+    private String username;
+    /**
+     * 使用部位
+     */
+    @ApiModelProperty("使用部位")
+    private String position;
+    /**
+     * 报告文件路径
+     */
+    @ApiModelProperty("报告文件路径")
+    @TableField("report_file_path")
+    private String reportFilePath;
+    /**
+     * 记录文件路径
+     */
+    @ApiModelProperty("记录文件路径")
+    @TableField("record_file_path")
+    private String recordFilePath;
+    /**
+     * 试验树id
+     */
+    @ApiModelProperty("实验树Id")
+    @TableField("exam_name_info_id")
+    public String examNameInfoId;
+    /**
+     * 试验树id
+     */
+    @ApiModelProperty("组装文件(报告+记录+委托单)")
+    @TableField("assemble_file")
+    public String assembleFile;
+    /**
+     * 附件
+     */
+    @ApiModelProperty("附件")
+    @TableField(exist = false)
+    private List<TrialCyAccessories> accessories;
+}

+ 54 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyTestType.java

@@ -0,0 +1,54 @@
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * 获取检测项目树(包括自建试验、外委、第三方、上传报告) 接受对象
+ *
+ * @author LHB
+ */
+@TableName("u_trial_cy_test_type")
+@Data
+public class TrialCyTestType {
+    @TableId(type = IdType.INPUT)
+    @ApiModelProperty("唯一id")
+    private Long pKeyId;
+    /**
+     * 项目id
+     */
+    @ApiModelProperty("项目id")
+    private Long projectId;
+    /**
+     * ID唯一标识
+     */
+    @TableField("id")
+    @ApiModelProperty("成渝的id")
+    private String id;
+    /**
+     * 名称
+     */
+    @TableField("name")
+    @ApiModelProperty("名称")
+    private String name;
+    /**
+     * 父级ID
+     */
+    @TableField("father_id")
+    @ApiModelProperty("父级id")
+    private String fatherId;
+    /**
+     * 顺序号
+     */
+    @TableField("order_index")
+    @ApiModelProperty("顺序号")
+    private String orderIndex;
+
+    @TableField(exist = false)
+    @ApiModelProperty("判断是否有子节点")
+    private Boolean hasChildren;
+}

+ 285 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialCyThirdReport.java

@@ -0,0 +1,285 @@
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+ * 获取已上传的外委检测报告/第三方检测报告/上传报告 接受对象
+ *
+ * @author LHB
+ */
+@TableName("u_trial_cy_third_report")
+@Data
+public class TrialCyThirdReport {
+    @ApiModelProperty("唯一id")
+    @TableId(type = IdType.INPUT)
+    private Long pKeyId;
+    /**
+     * 合同id
+     */
+    @ApiModelProperty("合同id")
+    private Long contractId;
+    /**
+     * ID
+     */
+    @ApiModelProperty("成渝的id")
+    @TableField("id")
+    public String id;
+    /**
+     * 报告类型(0:外委检测,1:第三方检测,2:扫描上传报告)
+     */
+    @ApiModelProperty("报告类型(0:外委检测,1:第三方检测,2:扫描上传报告)")
+    public Integer thirdType;
+    /**
+     * 委托编号
+     */
+    @ApiModelProperty("委托编号")
+    @TableField("consign_no")
+    public String consignNo;
+    /**
+     * 报告编号
+     */
+    @ApiModelProperty("报告编号")
+    @TableField("report_no")
+    public String reportNo;
+    /**
+     * 取样时间 格式如:“2022-06-21”
+     */
+    @ApiModelProperty("取样时间 格式如:“2022-06-21”")
+    @TableField("take_sampling_date")
+    public String takeSamplingDate;
+    /**
+     * 送样时间 格式如:“2022-06-21”
+     */
+    @ApiModelProperty("送样时间 格式如:“2022-06-21”")
+    @TableField("send_sample_date")
+    public String sendSampleDate;
+    /**
+     * 检测时间 格式如:“2022-06-21”
+     */
+    @ApiModelProperty("检测时间 格式如:“2022-06-21”")
+    @TableField("test_date")
+    public String testDate;
+    /**
+     * 报告时间 格式如:“2022-06-21”
+     */
+    @ApiModelProperty("报告时间 格式如:“2022-06-21”")
+    @TableField("report_date")
+    public String reportDate;
+    /**
+     * 委托单位
+     */
+    @ApiModelProperty("委托单位")
+    @TableField("consign_unit")
+    public String consignUnit;
+    /**
+     * 检测机构
+     */
+    @ApiModelProperty("检测机构")
+    @TableField("accept_test_unit")
+    public String acceptTestUnit;
+    /**
+     * 送样人
+     */
+    @ApiModelProperty("送样人")
+    @TableField("send_sample_person")
+    public String sendSamplePerson;
+    /**
+     * 接样人
+     */
+    @ApiModelProperty("接样人")
+    @TableField("witness_person")
+    public String witnessPerson;
+    /**
+     * 工程部位
+     */
+    @ApiModelProperty("工程部位")
+    @TableField("project_part")
+    public String projectPart;
+    /**
+     * 取样地点
+     */
+    @ApiModelProperty("取样地点")
+    @TableField("sampling_place")
+    public String samplingPlace;
+    /**
+     * 样品名称
+     */
+    @ApiModelProperty("样品名称")
+    @TableField("sample_name")
+    public String sampleName;
+    /**
+     * 委托单文件下载地址
+     */
+    @ApiModelProperty("委托单文件下载地址")
+    @TableField("consign_doc_file_path")
+    public String consignDocFilePath;
+    /**
+     * 记录单文件下载地址
+     */
+    @ApiModelProperty("记录单文件下载地址")
+    @TableField("record_doc_file_path")
+    public String recordDocFilePath;
+    /**
+     * 报告单文件下载地址
+     */
+    @ApiModelProperty("报告单文件下载地址")
+    @TableField("report_doc_file_path")
+    public String reportDocFilePath;
+    /**
+     * 检测依据
+     */
+    @ApiModelProperty("检测依据")
+    @TableField("test_standard")
+    public String testStandard;
+    /**
+     * 评定标准
+     */
+    @ApiModelProperty("评定标准")
+    @TableField("assess_standard")
+    public String assessStandard;
+    /**
+     * 检测结论
+     */
+    @ApiModelProperty("检测结论")
+    @TableField("test_conclusion")
+    public String testConclusion;
+    /**
+     * 备注
+     */
+    @ApiModelProperty("备注")
+    @TableField("memo")
+    public String memo;
+    /**
+     * 期数
+     */
+    @ApiModelProperty("期数")
+    @TableField("period_num")
+    public String periodNum;
+    /**
+     * 是否合格
+     */
+    @ApiModelProperty("是否合格:1 合格, 0 不合格")
+    @TableField("is_qualified")
+    public String isQualified;
+    /**
+     * 样品编号
+     */
+    @ApiModelProperty("样品编号")
+    @TableField("sample_code")
+    public String sampleCode;
+    /**
+     * 规格型号
+     */
+    @ApiModelProperty("规格型号")
+    @TableField("gui_ge_xing_hao")
+    public String guiGeXingHao;
+    /**
+     * 生产厂家
+     */
+    @ApiModelProperty("生产厂家")
+    @TableField("sheng_chan_cj")
+    public String shengChanCJ;
+    /**
+     * 产地
+     */
+    @ApiModelProperty("产地")
+    @TableField("chan_di")
+    public String chanDi;
+    /**
+     * 样品数量
+     */
+    @ApiModelProperty("样品数量")
+    @TableField("sample_num")
+    public String sampleNum;
+    /**
+     * 检测机构资质证书编号
+     */
+    @ApiModelProperty("检测机构资质证书编号")
+    @TableField("consign_unit_ability")
+    public String consignUnitAbility;
+    /**
+     * 批号
+     */
+    @ApiModelProperty("批号")
+    @TableField("batch_num")
+    public String batchNum;
+    /**
+     * 代表数量
+     */
+    @ApiModelProperty("代表数量")
+    @TableField("quantity")
+    public String quantity;
+    /**
+     * 单位
+     */
+    @ApiModelProperty("单位")
+    @TableField("unit")
+    public String unit;
+    /**
+     * 类型ID
+     */
+    @ApiModelProperty("类型ID")
+    @TableField("consign_test_cls_id")
+    public String consignTestClsID;
+    /**
+     * 结论
+     */
+    @ApiModelProperty("结论")
+    @TableField("result")
+    public String result;
+    /**
+     * 是否已删除
+     * Null:未删除
+     * 0:未删除
+     * 1:已删除
+     */
+    @ApiModelProperty("是否已删除 0:未删除 1:已删除")
+    @TableField("is_deleted")
+    public String isDeleted;
+    /**
+     * 删除时间
+     */
+    @ApiModelProperty("删除时间")
+    @TableField("delete_time")
+    public String deleteTime;
+    /**
+     * 快报/正式报告
+     * 1 快报
+     * 2 正式报告
+     */
+    @ApiModelProperty("快报/ 正式报告 1 快报 2 正式报告")
+    @TableField("report_type")
+    public Integer reportType;
+    /**
+     * 创建时间 格式如:“2022-06-21 13:44:33 235”
+     */
+    @ApiModelProperty("创建时间 格式如:“2022-06-21 13:44:33 235”")
+    @TableField("create_time")
+    public String createTime;
+    /**
+     * 试验树id
+     */
+    @ApiModelProperty("实验树Id")
+    @TableField("exam_name_info_id")
+    public String examNameInfoId;
+    /**
+     * 试验树id
+     */
+    @ApiModelProperty("组装文件(报告+记录+委托单)")
+    @TableField("assemble_file")
+    public String assembleFile;
+
+    /**
+     * 附件
+     */
+    @ApiModelProperty("附件")
+    @TableField(exist = false)
+    private List<TrialCyAccessories> accessories;
+}

+ 106 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/TrialSystemDocking.java

@@ -0,0 +1,106 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.entity;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.io.Serializable;
+import org.springblade.core.mp.base.BaseEntity;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 德飞试验系统对接表实体类
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@Data
+@TableName("u_trial_system_docking")
+public class TrialSystemDocking extends BaseEntity {
+
+	private static final long serialVersionUID = 1L;
+
+	/**
+	* 主键
+	*/
+	private Long id;
+	/**
+	 * 德飞ID
+	 */
+	private Long dataId;
+
+	/**
+	 * 项目Id
+	 */
+	private Long projectId;
+
+	private String classificationAncestors;
+	/**
+	* 报告文件名称
+	*/
+		private String reportName;
+	/**
+	* 报告编号
+	*/
+		private String reportNumber;
+	/**
+	* 单位名称
+	*/
+		private String unitName;
+	/**
+	* 所属检测分类id
+	*/
+		private Long classificationId;
+	/**
+	* 规格型号
+	*/
+		private String specification;
+	/**
+	* 报告类型(1原材检测报告,2现场检测报告,3外委报告,4第三方检测报告)
+	*/
+		private Integer reportType;
+	/**
+	* 工程用途及部位
+	*/
+		private String purposeLocation;
+	/**
+	* 报告日期(20250822)
+	*/
+		private String reportDate;
+	/**
+	* 原文件地址
+	*/
+		private String fileUrl;
+	/**
+	* 上传后文件地址
+	*/
+		private String fileUrlOss;
+	/**
+	* 负责人
+	*/
+		private String personInCharge;
+	/**
+	 * 是否删除
+ 	 */
+      private Integer isDeleted;
+
+	  /**
+	 * 是否更新OSS  1 是  0 否
+	 */
+	  private Integer isUpdateOss;
+
+}

+ 14 - 7
blade-service-api/blade-business-api/src/main/java/org/springblade/business/entity/WbsTreeContractStatistics.java

@@ -63,38 +63,38 @@ public class WbsTreeContractStatistics implements Serializable {
      * 叶子节点数量
      */
     @ApiModelProperty(value = "叶子节点数量")
-    private Integer leafNum = 0;
+    private Integer leafNum;
 
     /**
      * 已填报数量
      */
     @ApiModelProperty(value = "已填报数量")
-    private Integer fillNum = 0;
+    private Integer fillNum;
     /**
      * 待审批数量
      */
     @ApiModelProperty(value = "待审批数量")
-    private Integer approveNum = 0;
+    private Integer approveNum;
     /**
      * 已审批数量
      */
     @ApiModelProperty(value = "已审批数量")
-    private Integer completeNum = 0;
+    private Integer completeNum;
     /**
      * 已填报数量(监理)
      */
     @ApiModelProperty(value = "已填报数量(监理)")
-    private Integer jlFillNum = 0;
+    private Integer jlFillNum;
     /**
      * 待审批数量(监理)
      */
     @ApiModelProperty(value = "待审批数量(监理)")
-    private Integer jlApproveNum = 0;
+    private Integer jlApproveNum;
     /**
      * 已审批数量(监理)
      */
     @ApiModelProperty(value = "已审批数量(监理)")
-    private Integer jlCompleteNum = 0;
+    private Integer jlCompleteNum;
 
     @DateTimeFormat(
             pattern = "yyyy-MM-dd HH:mm:ss"
@@ -133,6 +133,13 @@ public class WbsTreeContractStatistics implements Serializable {
             this.ancestors = ancestors == null ? "" : ancestors;
             this.status = 1;
             this.isLeaf = 1;
+            this.fillNum = 0;
+            this.approveNum = 0;
+            this.completeNum = 0;
+            this.jlFillNum = 0;
+            this.jlApproveNum = 0;
+            this.jlCompleteNum = 0;
+            this.leafNum = 0;
         }
     }
 

+ 8 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/feign/ArchiveFileClient.java

@@ -4,7 +4,9 @@ import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+import org.springblade.archive.dto.FindAndReplaceDto;
 import org.springblade.archive.dto.SendsWebSocketArchiveDTO;
+import org.springblade.business.dto.FindAndReplaceDto1;
 import org.springblade.business.entity.ArchiveFile;
 import org.springblade.business.vo.ArchiveFileVO;
 import org.springblade.common.constant.BusinessConstant;
@@ -167,4 +169,10 @@ public interface ArchiveFileClient {
 
     @PostMapping(API_PREFIX + "/getArchiveFileByArchiveIds")
     List<ArchiveFile> getArchiveFileByArchiveIds(@RequestParam String archiveIds);
+
+    @PostMapping(API_PREFIX + "/findAndReplace")
+    boolean findAndReplace(@RequestBody FindAndReplaceDto1 dto1);
+
+    @PostMapping(API_PREFIX + "/getAllArchiveFileByIds")
+    List<ArchiveFile> getAllArchiveFileByIds(@RequestBody List<String> strList);
 }

+ 24 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/feign/TrialCyAccessoriesClient.java

@@ -0,0 +1,24 @@
+package org.springblade.business.feign;
+
+import com.alibaba.fastjson.JSONObject;
+import org.springblade.common.constant.BusinessConstant;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestParam;
+
+import java.util.List;
+
+/**
+ * @author LHB
+ */
+
+@FeignClient(value = BusinessConstant.APPLICATION_WEATHER_NAME)
+public interface TrialCyAccessoriesClient {
+    /**
+     * 接口前缀
+     */
+    String API_PREFIX = "/api/business/detection";
+
+    @PostMapping(API_PREFIX + "/getTrialFilePdfRecord")
+    List<JSONObject> getTrialFilePdfRecord(@RequestParam String primaryKeyId,@RequestParam List<Integer> list);
+}

+ 3 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/feign/WbsTreeContractStatisticsClient.java

@@ -45,4 +45,7 @@ public interface WbsTreeContractStatisticsClient {
     @GetMapping(API_PREFIX + "/statisticsContract")
     void statisticsContract(@RequestParam Long contractId);
 
+    @GetMapping(API_PREFIX + "/updateAncestors")
+    void updateAncestors(@RequestParam String ids);
+
 }

+ 45 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/ChekPdfPaceVo.java

@@ -0,0 +1,45 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.springblade.business.entity.ArchiveFile;
+
+/**
+ * 视图实体类
+ *
+ * @author BladeX
+ * @since 2022-07-08
+ */
+@Data
+public class ChekPdfPaceVo {
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 当前页
+     */
+    @ApiModelProperty("完成数量")
+    private Integer finishCount;
+
+    @ApiModelProperty("总数量")
+    private Integer totalCount;
+
+    @ApiModelProperty("完成比")
+    private double pace;
+}

+ 9 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/ContractLogVO.java

@@ -1,10 +1,13 @@
 package org.springblade.business.vo;
 
 import io.swagger.annotations.ApiModelProperty;
+import org.springblade.business.dto.StartTimeAndEndTime;
 import org.springblade.business.entity.ContractLog;
 import lombok.Data;
 import lombok.EqualsAndHashCode;
 
+import javax.validation.Valid;
+import javax.validation.constraints.NotEmpty;
 import java.util.ArrayList;
 import java.util.List;
 
@@ -49,6 +52,12 @@ public class ContractLogVO extends ContractLog {
     @ApiModelProperty(value = "签字人员集合")
     private List<Object> taskApproveUserNamesList;
 
+
+    @ApiModelProperty(value = "按月封装时间范围")
+    @NotEmpty(message = "请选择时间范围")
+    @Valid
+    private List<StartTimeAndEndTime> startTimeAndEndTimes;
+
     public void setSelectNodeList(String primaryKeyId, String title) {
         if (this.selectNodeList == null) {
             this.selectNodeList = new ArrayList<>();

+ 3 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/EntrustInfoVO.java

@@ -53,4 +53,7 @@ public class EntrustInfoVO extends EntrustInfo {
     @ApiModelProperty("任务Id")
     private String taskId;
 
+	@ApiModelProperty("委托单编号")
+	private String entrustNo;
+
 }

+ 13 - 3
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/InformationQueryVO.java

@@ -86,12 +86,17 @@ public class InformationQueryVO extends InformationQuery {
     private Integer waitingUserStatus;
 
 
+    @ApiModelProperty("重刷状态 0-待重刷,1-正在重刷,2-重刷成功,3-重刷失败")
+    private Integer saveAgain;
 
-    public void setWaitingUserList(String waitingUserName, Integer status) {
+    @ApiModelProperty("重刷次数:如果次数大于5次 每次都是3,就停止重刷")
+    private Integer saveAgainCount;
+
+    public void setWaitingUserList(String waitingUserName, Integer status, String userId) {
         if (this.waitingUserList == null) {
             this.waitingUserList = new ArrayList<>();
         }
-        this.waitingUserList.add(new WaitingUser(waitingUserName, status));
+        this.waitingUserList.add(new WaitingUser(waitingUserName, status, userId));
     }
 
     @Data
@@ -102,9 +107,14 @@ public class InformationQueryVO extends InformationQuery {
         @ApiModelProperty("审批状态,1未签字(黑色),2已签字(绿色),3已废除(黄色),999签字异常(红色)")
         private Integer status;
 
-        public WaitingUser(String waitingUserName, Integer status) {
+        @ApiModelProperty("用户ID")
+        private String userId;
+
+
+        public WaitingUser(String waitingUserName, Integer status, String userId) {
             this.waitingUserName = waitingUserName;
             this.status = status;
+            this.userId=userId;
         }
     }
 

+ 64 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/NeiYeLedgerVO.java

@@ -1,45 +1,74 @@
 package org.springblade.business.vo;
 
+import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
+import com.alibaba.excel.annotation.ExcelProperty;
+import com.alibaba.excel.annotation.write.style.ColumnWidth;
+import com.alibaba.excel.annotation.write.style.ContentRowHeight;
+import com.alibaba.excel.annotation.write.style.ContentStyle;
+import com.alibaba.excel.annotation.write.style.HeadRowHeight;
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
+import org.apache.poi.ss.usermodel.HorizontalAlignment;
 
 @Data
+@HeadRowHeight(20)
+@ContentRowHeight(18)
+//忽略为加excel注解的字段
+@ExcelIgnoreUnannotated
 public class NeiYeLedgerVO {
 
     /**
      * 单位工程
      */
     @ApiModelProperty(value = "单位工程")
+    @ExcelProperty(value = "单位工程",order = 1)
+    @ColumnWidth(30)
+    @ContentStyle(wrapped = true)
     private String unitProject;
 
     /**
      * 分部工程
      */
     @ApiModelProperty(value = "分部工程")
+    @ExcelProperty(value = "分部工程",order = 2)
+    @ColumnWidth(40)
+    @ContentStyle(wrapped = true)
     private String partProject;
 
     /**
      * 子分部工程
      */
     @ApiModelProperty(value = "子分部工程")
+    @ExcelProperty(value = "子分部工程",order = 3)
+    @ColumnWidth(40)
+    @ContentStyle(wrapped = true)
     private String partChildProject;
 
     /**
      * 分项工程
      */
     @ApiModelProperty(value = "分项工程")
+    @ExcelProperty(value = "分项工程",order = 4)
+    @ColumnWidth(40)
+    @ContentStyle(wrapped = true)
     private String subentryProject;
 
     /**
      * 子分项工程
      */
     @ApiModelProperty(value = "子分项工程")
+    @ExcelProperty(value = "子分项工程",order = 5)
+    @ColumnWidth(40)
+    @ContentStyle(wrapped = true)
     private String subentryChildProject;
 
     /**
      * 工序
      */
     @ApiModelProperty(value = "工序")
+    @ExcelProperty(value = "工序",order = 6)
+    @ColumnWidth(40)
+    @ContentStyle(wrapped = true)
     private String process;
 
     //施工台账信息 start ==================================
@@ -66,6 +95,9 @@ public class NeiYeLedgerVO {
      * 审批状态
      */
     @ApiModelProperty(value = "审批状态,1未上报,2待审批,3已审批")
+    @ExcelProperty(value = "审批状态",order = 7)
+    @ColumnWidth(15)
+    @ContentStyle(horizontalAlignment = HorizontalAlignment.CENTER)
     private String taskStatus;
 
     /**
@@ -85,6 +117,38 @@ public class NeiYeLedgerVO {
      */
     @ApiModelProperty(value = "information-query主键")
     private String id;
+    /**
+     * 是否填写了日期
+     */
+    @ApiModelProperty(value = "是否填写了日期")
+    @ExcelProperty(value = "日期是否完整",order = 9)
+    @ColumnWidth(20)
+    @ContentStyle(horizontalAlignment = HorizontalAlignment.CENTER)
+    private String dateIsComplete;
+    /**
+     * 文件提名
+     */
+    @ApiModelProperty(value = "文件提名")
+    @ExcelProperty(value = "文件提名",order = 8)
+    @ColumnWidth(100)
+    @ContentStyle(wrapped = true)
+    private String infoQueryName;
+
+    /**
+     * 文件pdf路径
+     */
+    @ApiModelProperty(value = "路径")
+    @ExcelProperty(value = "文件地址",order = 11)
+    @ColumnWidth(110)
+    private String pdfUrl;
+    /**
+     * 附件报告
+     */
+    @ApiModelProperty(value = "附件报告")
+    @ColumnWidth(100)
+    @ContentStyle(wrapped = true)
+    @ExcelProperty(value = "附件报告",order = 10)
+    private String fileTypeMsg;
 
     public NeiYeLedgerVO(String... values) {
         this.unitProject = values[0];

+ 9 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/NeiYeQueryVO.java

@@ -38,6 +38,15 @@ public class NeiYeQueryVO {
     @ApiModelProperty(value = "项目ID")
     private String contractIdRelation;
 
+    @ApiModelProperty(value = "是否缺少附件:true为完整")
+    private Boolean isFile;
+
+    @ApiModelProperty(value = "日期是否填报,与质检树类型一致")
+    private Integer dateIsComplete;
+
+    @ApiModelProperty(value = "查询类型:1-工序,2-节点")
+    private Integer selectType = 1;
+
     private List<String> wbsIds;
 
 }

+ 36 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/QueryProcessDataVO.java

@@ -33,4 +33,40 @@ public class QueryProcessDataVO {
 
     private String isExperiment;
 
+    /**
+     * 是否填写了日期
+     */
+    private String dateIsComplete;
+    /**
+     * 文件提名
+     */
+    private String infoQueryName;
+
+    /**
+     * 文件pdf路径
+     */
+    private String pdfUrl;
+    /**
+     * 文件pdf路径
+     */
+    private String privateTableFileType;
+    /**
+     * 文件pdf路径
+     */
+    private String contractTableFileType;
+    /**
+     * 文件pdf路径
+     */
+    private String contractTableFileTypeTwo;
+
+    /**
+     * 附件报告
+     */
+    private String fileTypeMsg;
+
+    /**
+     * 附件报告是否完整
+     */
+    private Boolean fileType = false;
+
 }

+ 72 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/RecycleBinInfoVO.java

@@ -0,0 +1,72 @@
+package org.springblade.business.vo;
+
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import org.springblade.core.mp.support.Query;
+
+import javax.validation.constraints.NotNull;
+import java.io.Serializable;
+import java.util.Date;
+
+
+@Data
+@EqualsAndHashCode(callSuper = true)
+public class RecycleBinInfoVO extends Query implements Serializable {
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 开始时间
+     */
+    @ApiModelProperty("开始时间")
+    private String startTime;
+    /**
+     * 结束时间
+     */
+    @ApiModelProperty("结束时间")
+    private String endTime;
+
+    /**
+     * 用户ID
+     */
+    @ApiModelProperty("用户ID")
+    private Long userId;
+
+    /**
+     * 合同段ID
+     */
+    @ApiModelProperty("合同段ID")
+    @NotNull
+    private Long contractId;
+
+    /**
+     * 是否是资料节点,0否,1是
+     */
+    @ApiModelProperty("是否是资料节点,0否,1是")
+    private Integer isData;
+
+    /**
+     * 0:删除台账, 1:恢复台账
+     */
+    @ApiModelProperty("0:删除台账, 1:恢复台账")
+    private Integer recycleType = 0;
+
+    /**
+     * 删除的类型,文件资料1,工程划分2,影像资料3
+     */
+    @ApiModelProperty("删除的类型,文件资料1,工程划分2,影像资料3")
+    private Integer delType = 2;
+
+    /**
+     * 内容
+     */
+    @ApiModelProperty("内容")
+    private String content;
+
+    @ApiModelProperty("操作记录id")
+    private String operationId;
+
+
+}

+ 13 - 3
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TaskApprovalVO.java

@@ -54,8 +54,8 @@ public class TaskApprovalVO {
     @ApiModelProperty("附件信息")
     private List<ApprovalFile> approvalFileList = new ArrayList<>();
 
-    public void setApprovalFileList(String fileName, String fileUrl) {
-        this.approvalFileList.add(new ApprovalFile(fileName, fileUrl));
+    public void setApprovalFileList(String fileName, String fileUrl, String nodeld, String classify, String projectId, String contractId) {
+        this.approvalFileList.add(new ApprovalFile(fileName, fileUrl, nodeld, classify, projectId, contractId));
     }
 
     @Data
@@ -65,9 +65,19 @@ public class TaskApprovalVO {
 
         private String fileUrl;
 
-        public ApprovalFile(String fileName, String fileUrl) {
+        // 由于质检任务需要查看附件pdf 需要假 4个字段
+        private String nodeld;
+        private String classify;
+        private String projectId;
+        private String contractId;
+
+        public ApprovalFile(String fileName, String fileUrl, String nodeld, String classify, String projectId, String contractId) {
             this.fileName = fileName;
             this.fileUrl = fileUrl;
+            this.nodeld = nodeld;
+            this.classify = classify;
+            this.projectId = projectId;
+            this.contractId = contractId;
         }
 
         public ApprovalFile() {

+ 20 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/ThirdReportVo.java

@@ -0,0 +1,20 @@
+package org.springblade.business.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author LHB
+ */
+@Data
+public class ThirdReportVo {
+    private Long id;
+    private Long contractId;
+    private String reportNo;
+    private String reportDate;
+    private String projectPositionName;
+    private String detectionResultName;
+
+    @ApiModelProperty(value = "是否关联选择过 0=否 1=是")
+    private Integer isSelectedStatus;
+}

+ 50 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TrialClassificationTreeVO.java

@@ -0,0 +1,50 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.vo;
+
+import org.springblade.business.entity.TrialClassificationTree;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * 德飞试验系统检测分类树视图实体类
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@Data
+public class TrialClassificationTreeVO  {
+	private static final long serialVersionUID = 1L;
+
+	/**
+	 * 主键
+	 */
+	private Long id;
+
+	private Long projectId;
+	/**
+	 * 父级ID
+	 */
+	private Long parentId;
+
+	private Boolean hasChildren;
+	/**
+	 * 分类名称
+	 */
+	private String classificationName;
+
+}

+ 32 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TrialCyThirdReportQueryVo.java

@@ -0,0 +1,32 @@
+package org.springblade.business.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import javax.validation.constraints.NotNull;
+
+/**
+ * 接口查询条件对象
+ * @author LHB
+ */
+@Data
+public class TrialCyThirdReportQueryVo {
+    private Integer current;
+    private Integer size;
+    @ApiModelProperty("开始时间")
+    private String startTime;
+    @ApiModelProperty("结束时间")
+    private String endTime;
+    @ApiModelProperty("树节点id")
+    @NotNull(message = "树节点id不能为空")
+    private Long nodeId;
+    @ApiModelProperty("合同段id")
+    @NotNull(message = "合同段id不能为空")
+    private Long contractId;
+    @ApiModelProperty("质检节点pkeyid")
+    private Long qualityTestPKeyId;
+    @ApiModelProperty("类型:0-外委检测,1-第三方")
+    private Integer type;
+    @ApiModelProperty("类型:0-施工,1-监理,2-业主")
+    private Integer reportType;
+}

+ 84 - 0
blade-service-api/blade-business-api/src/main/java/org/springblade/business/vo/TrialSystemDockingVO.java

@@ -0,0 +1,84 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.vo;
+
+import org.springblade.business.entity.TrialSystemDocking;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+import javax.validation.constraints.NotNull;
+
+/**
+ * 德飞试验系统对接表视图实体类
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@Data
+public class TrialSystemDockingVO {
+	private static final long serialVersionUID = 1L;
+
+	private Long id;
+
+	/**
+	 * 项目Id
+	 */
+	private Long projectId;
+	/**
+	 * 报告文件名称
+	 */
+	private String reportName;
+	/**
+	 * 报告编号
+	 */
+	private String reportNumber;
+	/**
+	 * 单位名称
+	 */
+	private String unitName;
+	/**
+	 * 所属检测分类id
+	 */
+
+	private Long classificationId;
+	/**
+	 * 规格型号
+	 */
+	private String specification;
+	/**
+	 * 报告类型(1原材检测报告,2现场检测报告,3外委报告,4第三方检测报告)
+	 */
+	private Integer reportType;
+	/**
+	 * 工程用途及部位
+	 */
+	private String purposeLocation;
+	/**
+	 * 报告日期(20250822)
+	 */
+	private String reportDate;
+	/**
+	 * 原文件地址
+	 */
+	private String fileUrl;
+	/**
+	 * 责任者
+	 */
+	private String personInCharge;
+
+
+}

+ 4 - 1
blade-service-api/blade-e-visa-api/src/main/java/org/springblade/evisa/vo/SealStrategyVO.java

@@ -74,9 +74,12 @@ public class SealStrategyVO {
     private String sealLocation;
 
     /**
-     * 签章原因,可以为空
+     * 用户名称
      */
     private String sealReason;
+
+    // 用户Id
+    private String userId;
     //坐标签章结束 ======================================
 
     /**

+ 50 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/dto/BatchAddNumbersDTO.java

@@ -0,0 +1,50 @@
+package org.springblade.manager.dto;
+
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+@Data
+@NoArgsConstructor
+@AllArgsConstructor
+public class BatchAddNumbersDTO {
+    @ApiModelProperty(value = "表单的pkeyId")
+    private Long pkeyId; //表单的pkeyId
+    @ApiModelProperty(value = "节点id")
+    private String nodeId; //节点id
+    @ApiModelProperty(value = "1施工 2监理")
+    private String classify; //1施工 2监理
+    @ApiModelProperty(value = "表单选中的key")
+    private String key; //表单选中的key
+    @ApiModelProperty(value = "1独立编号  2组合编号")
+    private Integer type;//  1独立编号  2组合编号
+
+    @ApiModelProperty(value = "1常规递增 2奇数递增 3偶数递增")
+    private Integer increType1; // 1常规递增 2奇数递增 3偶数递增
+    @ApiModelProperty(value = "1固定循环  2递增循环")
+    private Integer cycleType1; // 1固定循环  2递增循环
+    @ApiModelProperty(value = "循环组数")
+    private Integer cycleTypeGroup1; // 循环组数
+    @ApiModelProperty(value = "开始编号")
+    private Integer startNumber1; //开始编号
+    @ApiModelProperty(value = "结束编号")
+    private Integer endNumber1; //结束编号
+
+    /**
+     * 组合编号的情况才会有以下参数
+     */
+    @ApiModelProperty(value = "分隔符  - . / _ : 、")
+    private String separator; //分隔符  - . / _ : 、
+    @ApiModelProperty(value = "1常规递增 2奇数递增 3偶数递增")
+    private Integer increType2; // 1常规递增 2奇数递增 3偶数递增
+    @ApiModelProperty(value = "1固定循环  2递增循环")
+    private Integer cycleType2; // 1固定循环  2递增循环
+    @ApiModelProperty(value = "循环组数")
+    private Integer cycleTypeGroup2; // 循环组数
+    @ApiModelProperty(value = "开始编号")
+    private Integer startNumber2; //开始编号
+    @ApiModelProperty(value = "结束编号")
+    private Integer endNumber2; //结束编号
+}

+ 11 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/dto/MoveNodeDTO.java

@@ -0,0 +1,11 @@
+package org.springblade.manager.dto;
+
+import lombok.Data;
+
+import java.util.List;
+
+@Data
+public class MoveNodeDTO {
+    private List<Long> leftPkeyIds;
+    private Long rightPkeyId;
+}

+ 4 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/Album.java

@@ -61,6 +61,10 @@ public class Album extends BaseEntity {
 	*/
 		private String groupNumber;
 	/**
+	* 起止编号
+	*/
+		private String codes;
+	/**
 	* 开始日期
 	*/
 		private String startDate;

+ 36 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/AlbumImages.java

@@ -0,0 +1,36 @@
+package org.springblade.manager.entity;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+/**
+ * 相册与照片关联关系表
+ * @TableName m_album_images
+ */
+@TableName(value ="m_album_images")
+@Data
+public class AlbumImages {
+    /**
+     * id
+     */
+    @TableId
+    private Long id;
+
+    /**
+     * 相册表id
+     */
+    private Long albumId;
+
+    /**
+     * 照片表id
+     */
+    private Long imageId;
+    /**
+     * 照片表id
+     */
+    @TableField(exist = false)
+    private String imagesUrl;
+
+}

+ 5 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/ProjectInfo.java

@@ -211,4 +211,9 @@ public class ProjectInfo extends BaseEntity {
     private String jlSuffix;
 
 
+    /**
+     *
+     */
+    @ApiModelProperty(value = "短信时间")
+    private int msTime;
 }

+ 7 - 4
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/TableFile.java

@@ -16,10 +16,7 @@
  */
 package org.springblade.manager.entity;
 
-import com.baomidou.mybatisplus.annotation.IdType;
-import com.baomidou.mybatisplus.annotation.TableId;
-import com.baomidou.mybatisplus.annotation.TableLogic;
-import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.annotation.*;
 import com.fasterxml.jackson.databind.annotation.JsonSerialize;
 import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
 import io.swagger.annotations.ApiModel;
@@ -98,4 +95,10 @@ public class TableFile implements Serializable {
 
     private Integer sort;
 
+    /**
+     * 文件是否为关联的试验文件
+     */
+    @TableField(exist = false)
+    private Boolean isTrial = false;
+
 }

+ 67 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/WbsTreeContractExtend.java

@@ -0,0 +1,67 @@
+package org.springblade.manager.entity;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.util.Date;
+import lombok.Data;
+
+/**
+ * 合同段-扩展表
+ * @TableName m_wbs_tree_contract_extend
+ */
+@TableName(value ="m_wbs_tree_contract_extend")
+@Data
+public class WbsTreeContractExtend {
+    /**
+     * 
+     */
+    @TableId
+    private Long pKeyId;
+    /**
+     * 合同id
+     */
+    private Long contractId;
+
+    /**
+     *  类型(1-施工,2-监理)
+     */
+    private Integer type;
+    /**
+     *  是否为同步数据(1-是,0-不是)
+     */
+    private Integer isSync;
+    /**
+     *  节点祖级路径
+     */
+    private String ancestors;
+
+    /**
+     *  创建时间
+     */
+    private Date syncTime;
+
+    /**
+     *  是否删除(0-正常,1-已删除)
+     */
+    private Integer isDeleted;
+
+    /**
+     *  创建时间
+     */
+    private Date createTime;
+
+    /**
+     *  创建人
+     */
+    private Long createUser;
+
+    /**
+     *  修改时间
+     */
+    private Date updateTime;
+
+    /**
+     *  修改人
+     */
+    private Long updateUser;
+}

+ 61 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/WbsTreeContractOldHtml.java

@@ -0,0 +1,61 @@
+package org.springblade.manager.entity;
+
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.util.Date;
+import lombok.Data;
+
+/**
+ * 合同段表单上报之前的html记录
+ * @author LHB
+ * @TableName m_wbs_tree_contract_old_html
+ */
+@TableName(value ="m_wbs_tree_contract_old_html")
+@Data
+public class WbsTreeContractOldHtml {
+    /**
+     * 
+     */
+    @TableId
+    private Long id;
+
+    /**
+     * 合同WBS的p_key_id
+     */
+    private Long contractFormId;
+
+    /**
+     * 上报之前的html表单
+     */
+    private String oldHtmlUrl;
+
+    /**
+     * 上报之前的html表单
+     */
+    private String oldExcelUrl;
+
+    /**
+     *  是否删除(0-正常,1-已删除)
+     */
+    private Integer isDeleted;
+
+    /**
+     *  创建时间
+     */
+    private Date createTime;
+
+    /**
+     *  创建人
+     */
+    private Long createUser;
+
+    /**
+     *  修改时间
+     */
+    private Date updateTime;
+
+    /**
+     *  修改人
+     */
+    private Long updateUser;
+}

+ 2 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/entity/WbsTreePrivate.java

@@ -267,5 +267,7 @@ public class WbsTreePrivate extends BaseEntity {
     @ApiModelProperty(value = "是否包含单元评定")
     private Integer isClassifition;
 
+    @ApiModelProperty(value = "附件类型(复选)")
+    private String tableFileType;
 
 }

+ 18 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/INodeBaseInfoServiceClient.java

@@ -0,0 +1,18 @@
+package org.springblade.manager.feign;
+
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.RequestParam;
+
+import static org.springblade.core.launch.constant.AppConstant.APPLICATION_NAME_PREFIX;
+
+@FeignClient(value = APPLICATION_NAME_PREFIX + "manager")
+public interface INodeBaseInfoServiceClient {
+    /**
+     * 接口前缀
+     */
+    String API_PREFIX = "/api/manager/nodebaseinfo";
+
+    @GetMapping(API_PREFIX + "/getNameRuleByRule")
+    String getNameRuleByRule(@RequestParam String nameRule, @RequestParam String wbsId);
+}

+ 5 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsParamClient.java

@@ -1,6 +1,7 @@
 package org.springblade.manager.feign;
 
 
+import org.springblade.core.tool.api.R;
 import org.springblade.manager.entity.WbsParam;
 import org.springblade.manager.entity.WbsTreeContract;
 import org.springframework.cloud.openfeign.FeignClient;
@@ -9,6 +10,8 @@ import org.springframework.web.bind.annotation.PostMapping;
 import org.springframework.web.bind.annotation.RequestBody;
 import org.springframework.web.bind.annotation.RequestParam;
 
+import java.util.List;
+
 import static org.springblade.core.launch.constant.AppConstant.APPLICATION_NAME_PREFIX;
 
 @FeignClient(value = APPLICATION_NAME_PREFIX + "manager")
@@ -26,4 +29,6 @@ public interface WbsParamClient {
 
     @PostMapping(API_PREFIX + "/createFileTitle")
     String createFileTitle(@RequestBody WbsTreeContract contract);
+    @PostMapping(API_PREFIX + "/getNameRuleByPkeyId")
+    R<List<String>> getNameRuleByPkeyId(@RequestParam Long pKeyId, @RequestParam Long projectId);
 }

+ 7 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsTreeContractClient.java

@@ -1,6 +1,7 @@
 package org.springblade.manager.feign;
 
 import org.springblade.business.dto.EKeyDto;
+import org.springblade.core.tool.api.R;
 import org.springblade.manager.entity.ContractRelationJlyz;
 import org.springblade.manager.entity.WbsTreeContract;
 import org.springblade.manager.vo.AppWbsTreeContractVO;
@@ -205,4 +206,10 @@ public interface WbsTreeContractClient {
 
     @GetMapping(API_PREFIX + "/saveNameRuleByPkeyId")
     void saveNameRuleByPkeyId(@RequestParam Long  pKeyId, @RequestParam String s,  @RequestParam Long projectId);
+
+    @PostMapping(API_PREFIX + "/queryListByPIds")
+    List<WbsTreeContract> queryListByPIds(@RequestBody List<Long> pIds);
+
+    @PostMapping(API_PREFIX + "/findIsExistTreeNode")
+    Integer findIsExistTreeNode(@RequestBody List<String> ids);
 }

+ 25 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsTreeContractOldHtmlClient.java

@@ -0,0 +1,25 @@
+package org.springblade.manager.feign;
+
+import org.springblade.manager.entity.WbsTreeContract;
+import org.springblade.manager.entity.WbsTreeContractOldHtml;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
+
+import java.util.List;
+
+import static org.springblade.core.launch.constant.AppConstant.APPLICATION_NAME_PREFIX;
+
+@FeignClient(value = APPLICATION_NAME_PREFIX + "manager")
+public interface WbsTreeContractOldHtmlClient {
+    /**
+     * 接口前缀
+     */
+    String API_PREFIX = "/api/manager/WbsTreeContractOldHtml";
+
+    @PostMapping(API_PREFIX + "/save")
+    Boolean save(@RequestBody List<WbsTreeContractOldHtml> data);
+
+    @PostMapping(API_PREFIX + "/deleteByContractFormIds")
+    void deleteByContractFormIds(@RequestBody List<Long> collect);
+}

+ 84 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/APIWbsContractSubdivisionVo.java

@@ -0,0 +1,84 @@
+package org.springblade.manager.vo;
+
+import lombok.Data;
+import org.springblade.manager.entity.WbsTreeContract;
+
+/**
+ * 合同段分部分项划分节点试图
+ * 包含各个状态
+ * | 01   | 交工证书     | 所有子节点存在一个的major_data_type = 3   值为 true     |
+ * | 02   | 7天强度报告  | 所有最小节点中在m_table_file 中type = 11  存在一个true  |
+ * | 03   | 28天强度报告 | 所有最小节点中在m_table_file 中type = 12   存在一个true |
+ * | 04   | 监理收验资料 | 监理 major_data_type = 4  全部已审批                    |
+ * | 05   | 桩检报告     | 所有最小节点中在m_table_file 中type = 13   存在一个true |
+ * | 06   | 质检资料     | 质检 major_data_type = 4  全部已审批                    |
+ * | 07   | 评定资料     | major_data_type = 2  全部已审批                         |
+ * @author LHB
+ */
+@Data
+public class APIWbsContractSubdivisionVo {
+    /**
+     * 主键
+     */
+    private Long id;
+    /**
+     * 编码 空
+     */
+    private String code;
+    /**
+     * 节点名称
+     */
+    private String name;
+    /**
+     * 桩号
+     */
+    private String stake;
+    /**
+     * 父节点id
+     */
+    private Long pid;
+    /**
+     * 1表示单位工程 2表示分部工程 3表示分项工程
+     */
+    private Integer nodeType;
+    /**
+     * 层级编码 空
+     */
+    private String levelCode;
+    /**
+     * 专业工程id
+     */
+    private String partitionCatagID;
+    /**
+     * 专业工程名称
+     */
+    private String partitionCatagName;
+    /**
+     * 交工证书
+     */
+    private Boolean completionCertificate = false;
+    /**
+     * 7天强度报告
+     */
+    private Boolean strengthReportSeven = false;
+    /**
+     * 28天强度报告
+     */
+    private Boolean strengthReportTwentyEight = false;
+    /**
+     * 监理资料
+     */
+    private Boolean supervisionData = false;
+    /**
+     * 桩检报告
+     */
+    private Boolean pileInspectionReport = false;
+    /**
+     * 质检资料
+     */
+    private Boolean qualityInspectionData = false;
+    /**
+     * 评定资料
+     */
+    private Boolean evaluationData = false;
+}

+ 2 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/AppWbsTreeContractVO.java

@@ -21,4 +21,6 @@ public class AppWbsTreeContractVO extends WbsTreeContract {
     @ApiModelProperty(value = "文件题名")
     private String fileName;
 
+    @ApiModelProperty(value = "是否最近同步节点")
+    private Integer isSync;
 }

+ 2 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/ExceTabTreVO.java

@@ -63,6 +63,8 @@ public class ExceTabTreVO extends ExcelTab implements INode<ExceTabTreVO> {
     @JsonInclude(JsonInclude.Include.NON_EMPTY)
     private Boolean hasChildren;
 
+    private Integer tableOwner;
+
     @Override
     public List<ExceTabTreVO> getChildren() {
         if (this.children == null) {

+ 2 - 1
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/WbsTreeContractLazyVO.java

@@ -139,6 +139,7 @@ public class WbsTreeContractLazyVO implements Serializable {
     @ApiModelProperty(value = "是否完成日期填写1是2否")
     private Integer dateIsComplete;
 
-
+    @ApiModelProperty(value = "是否最近同步节点")
+    private Integer isSync;
 
 }

+ 6 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/WbsTreeContractTreeAllVO.java

@@ -41,6 +41,12 @@ public class WbsTreeContractTreeAllVO implements INode<WbsTreeContractTreeAllVO>
     @ApiModelProperty(value = "是否为自定义新增节点 1=是")
     private Integer isCustom;
 
+    @ApiModelProperty(value = "是否完成日期填写 1是 2否")
+    private Integer dateIsComplete;
+
+    @ApiModelProperty(value = "是否为自定义新增节点 1=是")
+    private Integer isSync;
+
     @JsonInclude(JsonInclude.Include.NON_EMPTY)
     private List<WbsTreeContractTreeAllVO> children;
 

+ 8 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/vo/WbsTreePrivateVO.java

@@ -6,9 +6,12 @@ import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
 import lombok.Data;
 import lombok.EqualsAndHashCode;
 import org.springblade.core.tool.node.INode;
+import org.springblade.core.tool.utils.StringUtil;
 import org.springblade.manager.entity.WbsTreePrivate;
 
 import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
 import java.util.List;
 
 @Data
@@ -68,5 +71,10 @@ public class WbsTreePrivateVO extends WbsTreePrivate implements INode<WbsTreePri
      */
     private Integer checkStatus = 0;
 
+    /**
+     * 附件类型
+     */
+    private List<String> tableFileTypes;
+
 
 }

+ 27 - 8
blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchiveFileController.java

@@ -10,9 +10,12 @@ import io.swagger.annotations.*;
 import lombok.AllArgsConstructor;
 import lombok.SneakyThrows;
 import org.apache.commons.lang.StringUtils;
+import org.springblade.archive.dto.FindAndReplaceDto;
+import org.springblade.archive.entity.ArchivesAuto;
 import org.springblade.archive.service.IArchivesAutoService;
 import org.springblade.archive.utils.FileUtils;
 import org.springblade.archive.vo.ArchiveDataVo;
+import org.springblade.business.dto.FindAndReplaceDto1;
 import org.springblade.business.entity.ArchiveFile;
 import org.springblade.business.feign.ArchiveFileClient;
 import org.springblade.business.feign.MetadataClassificationClient;
@@ -65,6 +68,7 @@ public class ArchiveFileController extends BladeController {
     private final MetadataClassificationClient metadataClassificationClient;
     private final IArchivesAutoService autoService;
     private final CommonFileClient commonFileClient;
+
     /**
      * 上传文件
      *
@@ -99,11 +103,11 @@ public class ArchiveFileController extends BladeController {
                 int i = 1;
                 for (ArchiveFileVO saveVo : saveList) {
                     try {
-                        if(StringUtils.isNotEmpty(saveVo.getPdfFileUrl())&&saveVo.getPageNum()==null){
+                        if (StringUtils.isNotEmpty(saveVo.getPdfFileUrl()) && saveVo.getPageNum() == null) {
                             String num = commonFileClient.getPdfNum(saveVo.getPdfFileUrl());
                             saveVo.setFilePage(Integer.valueOf(num));
                         }
-                    }catch (Exception e){
+                    } catch (Exception e) {
                         saveVo.setFilePage(0);
                     }
                     saveVo.setId(SnowFlakeUtil.getId());
@@ -156,8 +160,8 @@ public class ArchiveFileController extends BladeController {
         if (queryVo.getNodeIds().isEmpty() || queryVo.getNodeIds().equals("")) {
 
         } else {
-            ArchiveTreeContract rootNode=  this.archiveTreeContractClient.getArchiveTreeContractById(Long.parseLong(queryVo.getNodeIds()));
-            if (rootNode != null && rootNode.getExtType()!= null ) {
+            ArchiveTreeContract rootNode = this.archiveTreeContractClient.getArchiveTreeContractById(Long.parseLong(queryVo.getNodeIds()));
+            if (rootNode != null && rootNode.getExtType() != null) {
                 queryVo.setExtType(1);
             }
 
@@ -185,6 +189,7 @@ public class ArchiveFileController extends BladeController {
             this.archiveFileClient.updateArchiveFileSort(vo);
             try {
                 for (ArchiveFileVO saveVo : vo.getList()) {
+                    //获取源信息
                     metadataClassificationClient.createMetadataFile(saveVo.getId(), 0);
                 }
             } catch (Exception e) {
@@ -422,7 +427,7 @@ public class ArchiveFileController extends BladeController {
     @ApiOperation(value = "文件收集-上传文件责任者")
     public R getMetadataFile(String fileId) {
         long id;
-        try  {
+        try {
             fileId = fileId.split("_")[0];
             id = Long.parseLong(fileId);
         } catch (Exception e) {
@@ -454,8 +459,22 @@ public class ArchiveFileController extends BladeController {
     @PostMapping("/sendFileToEArchives")
     @ApiOperationSupport(order = 18)
     @ApiOperation(value = "智慧工地推送文件至电子档案数据规则接口")
-    public R<Boolean> sendFileToEArchives(@RequestBody ArchiveDataVo vo) {
-        //数据入库
-        return  autoService.sendFileToEArchives(vo);
+    public R<Boolean> sendFileToEArchives(@RequestBody List<ArchiveDataVo> vo) {
+        for (ArchiveDataVo v : vo) {
+            //数据入库
+            autoService.sendFileToEArchives(v);
+        }
+        return R.success("操作成功");
+    }
+
+
+
+   @PostMapping("/findAndReplace")
+    @ApiOperationSupport(order = 12)
+    @ApiOperation(value = "查找并替换", notes = "传入ids")
+    public R findAndReplace(@RequestBody FindAndReplaceDto dto){
+        List<ArchiveFile> archiveFiles = archiveFileClient.getAllArchiveFileByIds(Func.toStrList(dto.getIds()));
+        FindAndReplaceDto1 dto1 = new FindAndReplaceDto1(dto, archiveFiles);
+        return R.status(archiveFileClient.findAndReplace(dto1));
     }
 }

+ 8 - 2
blade-service/blade-archive/src/main/java/org/springblade/archive/controller/ArchivesAutoController.java

@@ -656,14 +656,20 @@ public class ArchivesAutoController extends BladeController {
 		//根据档号后缀排序 拿到第一个
 		ArchivesAuto auto = archivesAutoList.get(0);
 		//查出所有案卷文件
-		List<ArchiveFile>archiveFileList=archiveFileClient.getArchiveFileByArchiveIds(ids);
+		List<ArchiveFile>archiveFileList=new ArrayList<>();
+		List<Long> longList = Func.toLongList(ids);
+		for (Long id : longList) {
+			archiveFileList.addAll(archiveFileClient.getArchiveFileByArchiveIds(id+""));
+		}
 		//将除第一个以外的案卷文件archiveId 设置成第一个的id
 		List<ArchiveFile>updateArchiveFileList=new ArrayList<>();
+		int i=1;
 		for (ArchiveFile file : archiveFileList) {
 			if (!file.getArchiveId().equals(auto.getId())) {
 				file.setArchiveId(auto.getId());
-				updateArchiveFileList.add(file);
 			}
+			file.setArchiveSort(i++);
+			updateArchiveFileList.add(file);
 		}
 		archiveFileClient.updateArchiveFile(updateArchiveFileList);
 		auto.setName(name);

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

@@ -229,7 +229,7 @@ public interface ArchivesAutoMapper extends BaseMapper<ArchivesAuto> {
 	 */
 	Map<String, BigDecimal> getAllArchiveByContractTypeSummary(@Param("projectId") Long projectId,@Param("type") String typ);
 
-	String getArchiveFileByParentId(@Param("nodeId") String nodeId,@Param("contractId") String contractId);
+	Long getArchiveFileByParentId(@Param("nodeId") String nodeId,@Param("contractId") String contractId);
 
     List<ArchivesAutoVO4> selectAllArchiveAuto(@Param("projectId")Long projectId, @Param("contractId") Long contractId, @Param("nodeIds") List<String> nodeIds,@Param("isArchive")Integer isArchive);
 

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

@@ -1643,4 +1643,8 @@
         order by m.tree_sort,u.auto_file_sort is null ,u.auto_file_sort,u.file_number is null,
         SUBSTRING_INDEX(u.file_number, '_', 1), SUBSTRING_INDEX(u.file_number, '_', -1) + 0 ,u.create_time asc
     </select>
+    <select id="getArchiveFileByParentId" resultType="java.lang.Long">
+        select c.id from m_archive_tree_contract c left join m_archive_tree a on a.id=c.from_id where c.contract_id=#{contractId} and a.id=#{nodeId} and c.is_deleted=0 and a.is_deleted=0
+
+    </select>
 </mapper>

+ 12 - 2
blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchiveAutoPdfServiceImpl.java

@@ -742,12 +742,22 @@ public class ArchiveAutoPdfServiceImpl implements IArchiveAutoPdfService {
                                     CreationHelper helper = workbook.getCreationHelper();
                                     RichTextString richText = helper.createRichTextString(displayText);
 
+                                    // 🔴🔴🔴 新增:获取原单元格的字体样式 🔴🔴🔴
+                                    CellStyle originalStyle = cell.getCellStyle();
+                                    Font originalFont = workbook.getFontAt(originalStyle.getFontIndex());
+
                                     // 创建白色字体(用于"占位"两字)
                                     Font whiteFont = workbook.createFont();
-                                    whiteFont.setColor(IndexedColors.WHITE.getIndex());
+                                    // 🟢🟢🟢 修改:继承原字体属性 🟢🟢🟢
+                                    whiteFont.setFontName(originalFont.getFontName()); // 继承字体名称
+                                    whiteFont.setFontHeightInPoints(originalFont.getFontHeightInPoints()); // 继承字号
+                                    whiteFont.setColor(IndexedColors.WHITE.getIndex()); // 只修改颜色
 
                                     // 创建默认黑色字体(用于实际文本)
                                     Font defaultFont = workbook.createFont();
+                                    // 🟢🟢🟢 修改:继承原字体属性 🟢🟢🟢
+                                    defaultFont.setFontName(originalFont.getFontName());
+                                    defaultFont.setFontHeightInPoints(originalFont.getFontHeightInPoints());
                                     defaultFont.setColor(IndexedColors.BLACK.getIndex());
 
                                     // 🔴 修复:正确设置索引范围
@@ -756,7 +766,7 @@ public class ArchiveAutoPdfServiceImpl implements IArchiveAutoPdfService {
 
                                     // 剩余字符:黑色(从索引2开始)
                                     if (displayText.length() > 2) {
-                                        richText.applyFont(3, displayText.length() - 1, defaultFont);
+                                        richText.applyFont(2, displayText.length() , defaultFont);
                                     }
 
                                     // 3. 设置单元格值

+ 36 - 30
blade-service/blade-archive/src/main/java/org/springblade/archive/service/impl/ArchivesAutoServiceImpl.java

@@ -766,7 +766,7 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 	public List<Map<String, String>> getAllArchiveAgeByContractType(Long projectId) {
 		List<Map<String, String>> list = baseMapper.getAllArchiveAgeByContractType(projectId);
 		return list;
-	}
+}
 
 	@Override
 	public void splitArchvies(Long projectId, Long contractId, Long nodeId) {
@@ -3121,7 +3121,7 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 		for (ArchiveTreeContract contract : archiveTreeContracts) {
 			boolean isContractValid = contractId.toString().equals(contract.getTreeCode()) || contractId.equals(contract.getContractId());
 
-			if (StringUtils.isEmpty(treeCode)) {
+			if (StringUtils.isEmpty(treeCode) || treeCode.equals("S")) {
 				if (StringUtils.isNotEmpty(nodeId)) {
 					if (isNodeOrAncestor(contract, nodeId)) {
 						result.add(contract);
@@ -3204,14 +3204,14 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 			}
 
 			// 根据treeCode决定额外条件
-			boolean isOwnerContract = StringUtils.isEmpty(treeCode); // 业主合同段标识
+			boolean isOwnerContract = (StringUtils.isEmpty(treeCode) || treeCode.equals("S")); // 业主合同段标识
 			boolean passesOwnerCheck = contractId.toString().equals(contract.getTreeCode())
 					|| contractId.equals(contract.getContractId())
 					|| StringUtils.isEmpty(contract.getTreeCode());
 
 			if (isOwnerContract) {
 				// 业主合同段:仅需额外检查(nodeId为空时)
-				if (passesOwnerCheck) {
+				if (true) {
 					result.add(contract);
 				}
 			} else {
@@ -4579,7 +4579,7 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 		String[] ids = archiveIds.split(",");
 		for (String archiveId : ids) {
 			ArchivesAuto auto = baseMapper.selectById(archiveId);
-			String sql = "select * from u_archive_file where archive_id = " + archiveId + " and is_deleted = 0 order by sort,sort_num,create_time";
+			String sql = "SELECT u.* FROM u_archive_file u LEFT JOIN m_archive_tree_contract m ON u.node_id = m.id WHERE u.archive_id = "+archiveId+" AND u.is_deleted = 0 ORDER BY m.sort, u.sort, u.sort_num, u.create_time";
 			//List<ArchiveFile> archiveFiles = archiveFileClient.getArchiveFileByArchiveID(Long.valueOf(archiveId));
 			List<ArchiveFile> archiveFiles = jdbcTemplate.query(sql, new BeanPropertyRowMapper<>(ArchiveFile.class));
 			archiveAutoPdfService.buildArchiveFrontPdfs(projectId, auto, archiveFiles, true);
@@ -4784,11 +4784,11 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 			return R.fail("请根据接口文档上传参数");
 		}
 
-		String nodeId = dataInfo.getNodeId();
+		String nodeIdstr = dataInfo.getNodeId();
 		String contractId = dataInfo.getContractId();
 		String fileUrl = dataInfo.getFileUrl();
 		String fileName = dataInfo.getFileNmae();
-		if (nodeId == null || Func.isNull(nodeId)) {
+		if (nodeIdstr == null || Func.isNull(nodeIdstr)) {
 			return R.fail("请上传nodeId");
 		}
 		if (contractId == null || Func.isNull(contractId)) {
@@ -4807,30 +4807,33 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 		if (contractInfo == null) {
 			return R.fail("请传输正确的contractId");
 		}
-		//获取文件的父节点Id
-		String treeContractId = baseMapper.getArchiveFileByParentId(nodeId, contractId);
-		if (treeContractId == null || Func.isNull(treeContractId)) {
-			R.fail("请校验传输的nodeId和contractId,没有查到父节点Id");
-		}
-
 
-		// 将数据插入到 auto表中
-		ArchivesAuto archivesAuto = new ArchivesAuto();
-		long newPkId = SnowFlakeUtil.getId(); //主键Id
-		archivesAuto.setId(newPkId);
-		archivesAuto.setProjectId(Func.toLong(contractInfo.getPId()));
-		archivesAuto.setContractId(Func.toLong(contractId));
-		archivesAuto.setName(fileName);
-		archivesAuto.setIsDeleted(0);
-		this.save(archivesAuto);
-
-		// 保存文件到archive_file表中
-		long arueId = SnowFlakeUtil.getId(); //主键Id
-		ArchiveFile archiveFile = new ArchiveFile();
-		archiveFile.setId(arueId);
-		archiveFile.setArchiveId(newPkId);
-		archiveFile.setFileName(fileName);
-		archiveFileClient.saveArchiveFileByBIM(archiveFile);
+		String[] nodeIds = nodeIdstr.split(",");
+		for (String  nodeId: nodeIds) {
+			//获取文件的父节点Id
+			Long treeContractId = baseMapper.getArchiveFileByParentId(nodeId, contractId);
+			if (treeContractId == null || Func.isNull(treeContractId)) {
+				R.fail("请校验传输的nodeId和contractId,没有查到父节点Id");
+			}
+			// 将数据插入到 auto表中
+			ArchivesAuto archivesAuto = new ArchivesAuto();
+			long newPkId = SnowFlakeUtil.getId(); //主键Id
+			archivesAuto.setId(newPkId);
+			archivesAuto.setProjectId(Func.toLong(contractInfo.getPId()));
+			archivesAuto.setContractId(Func.toLong(contractId));
+			archivesAuto.setName(fileName);
+			archivesAuto.setIsDeleted(0);
+			archivesAuto.setNodeId(treeContractId);
+			this.save(archivesAuto);
+
+			// 保存文件到archive_file表中
+			long arueId = SnowFlakeUtil.getId(); //主键Id
+			ArchiveFile archiveFile = new ArchiveFile();
+			archiveFile.setId(arueId);
+			archiveFile.setArchiveId(newPkId);
+			archiveFile.setFileName(fileName);
+			archiveFileClient.saveArchiveFileByBIM(archiveFile);
+		}
 		return R.success("保存成功");
 	}
 
@@ -5025,6 +5028,7 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 		// 多个组的进行合并组操作
 		List<List<ArchiveFile>> nodeGroups = new ArrayList<>(nodeGroupMap.values());
 		List<List<ArchiveFile>> mergedGroups = new ArrayList<>();
+		List<Integer> mergedGroupsPageCount =  new ArrayList<>();
 
 		int i = 0;
 		while (i < nodeGroups.size()) {
@@ -5034,6 +5038,7 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 			// 如果第一组页数和大于350,则第一组不合并
 			if (currentPages > 350) {
 				mergedGroups.add(currentMergedGroup);
+				mergedGroupsPageCount.add(currentPages);
 				i++;
 				continue;
 			}
@@ -5056,6 +5061,7 @@ public class ArchivesAutoServiceImpl extends BaseServiceImpl<ArchivesAutoMapper,
 			}
 
 			mergedGroups.add(currentMergedGroup);
+			mergedGroupsPageCount.add(currentPages);
 			i = j; // 从下一个未处理的组继续
 		}
 

+ 1 - 0
blade-service/blade-business/pom.xml

@@ -34,6 +34,7 @@
         <dependency>
             <groupId>org.springblade</groupId>
             <artifactId>blade-core-test</artifactId>
+            <scope>test</scope>
         </dependency>
         <dependency>
             <groupId>org.springblade</groupId>

+ 42 - 0
blade-service/blade-business/src/main/java/org/springblade/business/controller/ContractLogController.java

@@ -5,6 +5,7 @@ import com.alibaba.fastjson.JSONObject;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiImplicitParam;
@@ -44,6 +45,7 @@ import org.springframework.beans.BeanUtils;
 import org.springframework.jdbc.core.BeanPropertyRowMapper;
 import org.springframework.jdbc.core.JdbcTemplate;
 import org.springframework.transaction.annotation.Transactional;
+import org.springframework.validation.annotation.Validated;
 import org.springframework.web.bind.annotation.*;
 
 import java.io.IOException;
@@ -664,4 +666,44 @@ public class ContractLogController extends BladeController {
         return R.data(this.wbsTreeContractClient.queryCurrentContractLogList(contractId));
     }
 
+
+    /**
+     * 按月打包
+     *
+     * @param logVo 查询条件
+     * @return 结果
+     */
+    @PostMapping("/byMonthPack")
+    @ApiOperationSupport(order = 2)
+    @ApiOperation(value = "按月打包")
+    public R<Boolean> byMonthPack(@RequestBody @Validated ContractLogVO logVo) {
+        return R.data(this.contractLogService.byMonthPack(logVo));
+    }
+
+    /**
+     * 查询按月打包
+     *
+     * @param logVo 查询条件
+     * @return 结果
+     */
+    @PostMapping("/selectByMonthPack")
+    @ApiOperationSupport(order = 2)
+    @ApiOperation(value = "查询按月打包")
+    public R<Page<ContractLogMonthPack>> selectByMonthPack(@RequestBody ContractLogVO logVo) {
+        return R.data(this.contractLogService.selectByMonthPack(logVo));
+    }
+
+    /**
+     * 删除按月打包
+     *
+     * @param id id
+     * @return 结果
+     */
+    @GetMapping("/deleteByMonthPack")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "删除按月打包")
+    @ApiImplicitParam(name = "id", value = "id", required = true)
+    public R<Boolean> deleteByMonthPack(@RequestParam Long id) {
+        return R.data(this.contractLogService.deleteByMonthPack(id));
+    }
 }

+ 182 - 76
blade-service/blade-business/src/main/java/org/springblade/business/controller/InformationWriteQueryController.java

@@ -7,6 +7,7 @@ import com.alibaba.fastjson.JSONObject;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
 import com.baomidou.mybatisplus.core.toolkit.ObjectUtils;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
 import com.baomidou.mybatisplus.extension.conditions.query.QueryChainWrapper;
@@ -86,6 +87,9 @@ import javax.servlet.http.HttpServletResponse;
 import javax.validation.Valid;
 import java.io.*;
 import java.net.URLEncoder;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.StandardCopyOption;
 import java.time.LocalDateTime;
 import java.time.format.DateTimeFormatter;
 import java.util.*;
@@ -112,6 +116,7 @@ public class InformationWriteQueryController extends BladeController {
     private final ContractClient contractClient;
 
     private final WbsTreeContractClient wbsTreeContractClient;
+    private final WbsTreeContractOldHtmlClient wbsTreeContractOldHtmlClient;
 
     private final WbsTreePrivateClient wbsTreePrivateClient;
 
@@ -157,6 +162,8 @@ public class InformationWriteQueryController extends BladeController {
 
     private final IRecycleBinService recycleBinService;
     private final WbsTreeContractStatisticsClientImpl wbsTreeContractStatisticsClient;
+    private final IRecycleBinInfoService recycleBinInfoService;
+    private final INodeBaseInfoServiceClient nodeBaseInfoServiceClient;
 
 
     @Autowired
@@ -215,7 +222,7 @@ public class InformationWriteQueryController extends BladeController {
         String sgSuffix="";
         String jlSuffix="";
         if(queryList.size()>0){
-            String sql1="Select sg_suffix,jl_suffix from m_project_info where id="+queryList.get(0).getProjectId()+" and is_deleted=0";
+            String sql1="Select sg_suffix,jl_suffix,template_type from m_project_info where id="+queryList.get(0).getProjectId()+" and is_deleted=0";
             List<ProjectInfo> projectInfos = jdbcTemplate.query(sql1, new BeanPropertyRowMapper<>(ProjectInfo.class));
             if(projectInfos.size()>0){
                 sgSuffix=projectInfos.get(0).getSgSuffix()==null?"":projectInfos.get(0).getSgSuffix();
@@ -226,7 +233,16 @@ public class InformationWriteQueryController extends BladeController {
                 String sql="select * from m_wbs_tree_contract where p_key_id="+query.getWbsId()+" and is_deleted=0";
                 WbsTreeContract contract = jdbcTemplate.queryForObject(sql, new BeanPropertyRowMapper<>(WbsTreeContract.class));
                 if(dto.getType()==1){
-                    result=wbsParamClient.createFileTitle(contract);
+                    R<List<String>>  nameRuleList = wbsParamClient.getNameRuleByPkeyId(contract.getPKeyId(), Long.valueOf(contract.getProjectId()));
+                    String nameRule = "";
+                    if (nameRuleList != null && nameRuleList.getData() != null && !nameRuleList.getData().isEmpty()) {
+                        nameRule = String.join("-", nameRuleList.getData());
+                    }
+                    if(projectInfos.get(0)!=null&&projectInfos.get(0).getTemplateType()==2){
+                        result  = nodeBaseInfoServiceClient.getNameRuleByRule(nameRule, contract.getPKeyId()+"");
+                    }else {
+                        result=wbsParamClient.createFileTitle(contract);
+                    }
                 }else {
                     result=nodeNameMap.get(query.getId());
                     //同时修改工程划分节点命名规则
@@ -260,6 +276,7 @@ public class InformationWriteQueryController extends BladeController {
         return R.status(this.informationQueryService.updateBatchById(queryList));
     }
 
+
     public List<String> getNameRuleByPkeyId(Long pKeyId, Long projectId) {
         NameRuleVo vo = new NameRuleVo();
         String sql2="select * from m_wbs_param where node_id="+pKeyId+" and type=200"+" and is_deleted=0 and k='FILE_TITLE'";
@@ -391,13 +408,14 @@ public class InformationWriteQueryController extends BladeController {
             if(StringUtils.isEmpty(dto1.getNameRule())){
                 throw new ServiceException("请输入题名规则");
             }
-            String sql="select p_key_id,ancestors_p_id from m_wbs_tree_contract where p_key_id="+dto1.getWbsId()+" and is_deleted=0";
-            WbsTreeContract contract = jdbcTemplate.queryForObject(sql, new BeanPropertyRowMapper<>(WbsTreeContract.class));
-            String result="";
-            if(contract!=null){
-                result= createFileTitle(contract, dto1.getNameRule());
-            }
-            list.add(new PreviewNodeNameVO1(dto1.getWbsId(),result));
+           String result=nodeBaseInfoServiceClient.getNameRuleByRule(dto1.getNameRule(),dto1.getWbsId());
+//            String sql="select p_key_id,ancestors_p_id from m_wbs_tree_contract where p_key_id="+dto1.getWbsId()+" and is_deleted=0";
+//            WbsTreeContract contract = jdbcTemplate.queryForObject(sql, new BeanPropertyRowMapper<>(WbsTreeContract.class));
+//            String result="";
+//            if(contract!=null){
+//                result= createFileTitle(contract, dto1.getNameRule());
+//            }
+            list.add(new PreviewNodeNameVO1(dto1.getWbsId(),result.toString()));
         }
         return R.data(list);
     }
@@ -412,7 +430,7 @@ public class InformationWriteQueryController extends BladeController {
             WbsTreeContract contract = jdbcTemplate.queryForObject(sql, new BeanPropertyRowMapper<>(WbsTreeContract.class));
             String result="";
             if(nameRules!=null){
-                result= createFileTitle(contract, String.join("-", nameRules));
+                result = nodeBaseInfoServiceClient.getNameRuleByRule(String.join("-", nameRules), contract.getPKeyId() + "");
             }
             list.add(new PreviewNodeNameVO(dto.getWbsId(),result,nameRules));
         }
@@ -1212,8 +1230,48 @@ public class InformationWriteQueryController extends BladeController {
                 return R.data(300, false, "未查询到填报信息,上报失败");
             }
         } else { //质检
+            //记录选中节点的所有表单旧html
+            List<Long> list = Arrays.stream(startTaskVO.getIds().split(",")).map(Long::parseLong).collect(Collectors.toList());
+            List<WbsTreeContract> wbsTreeContracts =  wbsTreeContractClient.queryListByPIds(list);
+
+
             businessData = this.informationQueryService.getOne(Wrappers.<InformationQuery>lambdaQuery().eq(InformationQuery::getWbsId, startTaskVO.getIds().replaceAll(",", "")).eq(InformationQuery::getClassify, startTaskVO.getClassify().toString()).eq(InformationQuery::getType, 1).last("order by id desc limit 1"));
             if (businessData != null) {
+
+                //处理html 复制之后记录在新表中w
+                if (CollectionUtils.isNotEmpty(wbsTreeContracts)) {
+                    List<WbsTreeContractOldHtml> data = new ArrayList<>();
+                    try {
+                        for (WbsTreeContract wbsTreeContract : wbsTreeContracts) {
+                            ExcelTab byId = excelTabClient.getById(String.valueOf(wbsTreeContract.getExcelId()));
+                            WbsTreeContractOldHtml oldHtml = new WbsTreeContractOldHtml();
+                            oldHtml.setId(SnowFlakeUtil.getId());
+                            oldHtml.setCreateUser(getUser().getUserId());
+                            String htmlUrl = wbsTreeContract.getHtmlUrl();
+                            // 获取或下载文件
+                            Path sourcePath = FileUtils.getOrDownloadFile(htmlUrl);
+                            // 生成副本路径
+                            Path copyPath = FileUtils.generateCopyPath(sourcePath,wbsTreeContract.getPKeyId());
+                            // 执行复制操作(覆盖已存在的文件)
+                            Files.copy(sourcePath, copyPath, StandardCopyOption.REPLACE_EXISTING);
+
+                            oldHtml.setContractFormId(wbsTreeContract.getPKeyId());
+                            oldHtml.setOldHtmlUrl(copyPath.toFile().getAbsolutePath());
+                            //记录历史excel路径
+                            oldHtml.setOldExcelUrl(byId.getFileUrl());
+                            data.add(oldHtml);
+                        }
+                        List<Long> collect = data.stream().map(WbsTreeContractOldHtml::getContractFormId).collect(Collectors.toList());
+                        //删除旧记录
+                        wbsTreeContractOldHtmlClient.deleteByContractFormIds(collect);
+
+                        wbsTreeContractOldHtmlClient.save(data);
+                    } catch (Exception e) {
+                        e.printStackTrace();
+                        throw new ServiceException(e.getMessage());
+                    }
+                }
+
                 //设置业务数据ID
                 startTaskVO.setIds(businessData.getId().toString());
                 return this.batchTask(startTaskVO);
@@ -1961,11 +2019,14 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
 
             //旧节点的pkeyId和新节点的pkeyId
             Map<Long, Long> oldPKeyIdToNewPKeyIdMap = new HashMap<>();
+            Map<Long, Long> oldIdToNewIdMap = new HashMap<>();
             //节点和表的id 与 节点/表 实体类
             Map<String, WbsTreeContract> nodeMap = new HashMap<>();
 
             nodeChildAll.forEach(node -> {
-                oldPKeyIdToNewPKeyIdMap.put(node.getPKeyId(),SnowFlakeUtil.getId());
+                Long id = SnowFlakeUtil.getId();
+                oldPKeyIdToNewPKeyIdMap.put(node.getPKeyId(), id);
+                oldIdToNewIdMap.put(node.getId(), id);
                 oldToNewIdMap.put(node.getId(), SnowFlakeUtil.getId());
                 nodeMap.put(node.getId().toString(), node);
             });
@@ -1981,53 +2042,55 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
                         .distinct()
                         .collect(Collectors.toList());
                 //表名集合转逗号拼接的字符串
-                String inClausePlaceholders = String.join(",", Collections.nCopies(tabNames.size(), "?"));
-                String sql = "SELECT table_name AS queryType, GROUP_CONCAT(COLUMN_name) AS ancestors " +
-                        "FROM information_schema.COLUMNS WHERE table_name IN (" + inClausePlaceholders + ") " +
-                        "GROUP BY table_name";
-                Object[] params = tabNames.toArray();
-                //数据库中查询 表与表对应的列名
-                List<Map<String, Object>> results = jdbcTemplate.queryForList(sql, params);
-
-                //表名集合转Map key=表名 value=表对应的数据集合
-                Map<String, List<WbsTreeContract>> tabsGroup = nodeChildAll.stream()
-                        .filter(f -> f.getType() == 2 && ObjectUtil.isNotEmpty(f.getInitTableName()))
-                        .collect(Collectors.groupingBy(WbsTreeContract::getInitTableName));
-
-                Set<Long> continuePkeyIds = new HashSet<>();
-                for (Map<String, Object> result : results) {
-                    String tabName = (String) result.get("queryType");
-                    String col = (String) result.get("ancestors");
-                    if (ObjectUtil.isEmpty(col) || ObjectUtil.isEmpty(tabName)) {
-                        continue;
-                    }
-                    //字段集合 过滤掉不存在指定字段的表
-                    List<String> filteredList = Arrays.stream(col.split(","))
-                            .filter(value -> !value.equals("id") && !value.equals("p_key_id") && !value.equals("group_id"))
-                            .collect(Collectors.toList());
-                    //过滤之后的字段集合
-                    String keys = StringUtils.join(filteredList, ",");
-                    //根据表明查询指定数据集合
-                    List<WbsTreeContract> tabs = tabsGroup.get(tabName);
-                    for (WbsTreeContract tab : tabs) {
-                        // 在复制数据时,测量记录表 的数据不需要复制
-                        if(tab.getType()==2 && tab.getTableType()==6){
+                if (!tabNames.isEmpty()) {
+                    String inClausePlaceholders = String.join(",", Collections.nCopies(tabNames.size(), "?"));
+                    String sql = "SELECT table_name AS queryType, GROUP_CONCAT(COLUMN_name) AS ancestors " +
+                            "FROM information_schema.COLUMNS WHERE table_name IN (" + inClausePlaceholders + ") " +
+                            "GROUP BY table_name";
+                    Object[] params = tabNames.toArray();
+                    //数据库中查询 表与表对应的列名
+                    List<Map<String, Object>> results = jdbcTemplate.queryForList(sql, params);
+
+                    //表名集合转Map key=表名 value=表对应的数据集合
+                    Map<String, List<WbsTreeContract>> tabsGroup = nodeChildAll.stream()
+                            .filter(f -> f.getType() == 2 && ObjectUtil.isNotEmpty(f.getInitTableName()))
+                            .collect(Collectors.groupingBy(WbsTreeContract::getInitTableName));
+
+                    Set<Long> continuePkeyIds = new HashSet<>();
+                    for (Map<String, Object> result : results) {
+                        String tabName = (String) result.get("queryType");
+                        String col = (String) result.get("ancestors");
+                        if (ObjectUtil.isEmpty(col) || ObjectUtil.isEmpty(tabName)) {
                             continue;
                         }
-                        //根据字段
-                        String dataSql = "SELECT " + keys + " FROM " + tabName + " WHERE p_key_id = " + tab.getPKeyId() + " LIMIT 1;";
-                        try {
-                            //查询指定表指定表节点的数据
-                            Map<String, Object> resultMap = jdbcTemplate.queryForMap(dataSql);
-                            //删除空值
-                            resultMap.values().removeIf(value -> value == null || (value instanceof String && ObjectUtil.isEmpty(value)));
-                            colMaps.put(tab.getPKeyId(), resultMap);
-                        } catch (EmptyResultDataAccessException e) {
-                            continuePkeyIds.add(tab.getPKeyId());
+                        //字段集合 过滤掉不存在指定字段的表
+                        List<String> filteredList = Arrays.stream(col.split(","))
+                                .filter(value -> !value.equals("id") && !value.equals("p_key_id") && !value.equals("group_id"))
+                                .collect(Collectors.toList());
+                        //过滤之后的字段集合
+                        String keys = StringUtils.join(filteredList, ",");
+                        //根据表明查询指定数据集合
+                        List<WbsTreeContract> tabs = tabsGroup.get(tabName);
+                        for (WbsTreeContract tab : tabs) {
+                            // 在复制数据时,测量记录表 的数据不需要复制
+                            if(tab.getType()==2 && tab.getTableType()==6){
+                                continue;
+                            }
+                            //根据字段
+                            String dataSql = "SELECT " + keys + " FROM " + tabName + " WHERE p_key_id = " + tab.getPKeyId() + " LIMIT 1;";
+                            try {
+                                //查询指定表指定表节点的数据
+                                Map<String, Object> resultMap = jdbcTemplate.queryForMap(dataSql);
+                                //删除空值
+                                resultMap.values().removeIf(value -> value == null || (value instanceof String && ObjectUtil.isEmpty(value)));
+                                colMaps.put(tab.getPKeyId(), resultMap);
+                            } catch (EmptyResultDataAccessException e) {
+                                continuePkeyIds.add(tab.getPKeyId());
+                            }
                         }
                     }
+                    logger.info("以下元素表没有获取到对应实体表数据,已跳过 ===> 表pKeyId:[{}]", StringUtils.join(continuePkeyIds, ","));
                 }
-                logger.info("以下元素表没有获取到对应实体表数据,已跳过 ===> 表pKeyId:[{}]", StringUtils.join(continuePkeyIds, ","));
             }
             // 节点+表节点
             for (WbsTreeContract nodeOld : nodeChildAll) {
@@ -2080,7 +2143,7 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
                     //如果不是  判断旧节点的父级id是否在旧节点集合中 如果在 则设置新节点的父级id为旧节点的父级id的映射id  否则就是随机id
                     newData.setParentId(oldToNewIdMap.containsKey(nodeOld.getParentId()) ? oldToNewIdMap.get(nodeOld.getParentId()) : SnowFlakeUtil.getId());
                     //TODO 20250414-lhb-新增
-                    newData.setPId(oldPKeyIdToNewPKeyIdMap.containsKey(nodeOld.getPId()) ? oldPKeyIdToNewPKeyIdMap.get(nodeOld.getPId()) : SnowFlakeUtil.getId());
+                    newData.setPId(oldPKeyIdToNewPKeyIdMap.containsKey(nodeOld.getPId()) ? oldPKeyIdToNewPKeyIdMap.get(nodeOld.getPId()) : oldToNewIdMap.get(nodeOld.getParentId()) ==  null ? SnowFlakeUtil.getId() : oldToNewIdMap.get(nodeOld.getParentId()));
                 }
                 newData.setCreateTime(new Date());
                 newData.setUpdateTime(new Date());
@@ -2480,8 +2543,9 @@ private Map<String, String> reviseValue(WbsTreeContract wtc, WbsTreeContract par
     if (wtc != null) {
         try {
             String tableName = wtc.getInitTableName();
-            if (!ekvMap.containsKey(tableName)) {
-                Map<String, String> map = ekvMap.computeIfAbsent(wtc.getInitTableName(), K -> new HashMap<>());
+//            if (!ekvMap.containsKey(tableName)) {
+//                Map<String, String> map = ekvMap.computeIfAbsent(wtc.getInitTableName(), K -> new HashMap<>());
+                Map<String, String> map = new HashMap<>();
                 if (parent == null) {
                     parent = this.wbsTreeContractClient.getContractWbsTreeByContractIdAndId(wtc.getParentId(), Long.parseLong(wtc.getContractId()));
                 }
@@ -2517,8 +2581,9 @@ private Map<String, String> reviseValue(WbsTreeContract wtc, WbsTreeContract par
                         });
                     }
                 }
-            }
-            return ekvMap.getOrDefault(tableName, new HashMap<>());
+//            }
+//            return ekvMap.getOrDefault(tableName, new HashMap<>());
+            return map;
         } catch (Exception e) {
             e.printStackTrace();
         }
@@ -2573,7 +2638,11 @@ private Object reviseValue(Map<String, String> p2, String key, Object value) {
                     /*重做随机值*/
                     List<RangeJson> rjs = JSON.parseArray(setting, RangeJson.class);
                     if (value != null && !value.toString().isEmpty() && Func.isNotEmpty(rjs)) {
-                        List<RangeJson> rangeJsons = rjs.stream().filter(rj -> rj.getPkeyId().equals(pKeyId)).collect(Collectors.toList());
+                        List<RangeJson> temp = rjs.stream().filter(rj -> rj.getPkeyId().equals(pKeyId)).collect(Collectors.toList());
+                        if (temp.isEmpty()) {
+                            temp = rjs;
+                        }
+                        List<RangeJson> rangeJsons = temp;
                         if (!rangeJsons.isEmpty()) {
                             List<String[]> la = Arrays.stream(value.toString().split("☆")).map(s -> s.split("_\\^_")).collect(Collectors.toList());
                             /*全部为一个数的时候不用修改*/
@@ -3642,23 +3711,21 @@ public R removeContractTreeNodeJudge(@RequestParam String ids) {
                 String wbsIds = removeList.stream().map(Object::toString).collect(Collectors.joining(","));
                 /** 判断是否子节点有上报或审批过的资料,因为父id和祖级节点错误,直接使用上面的值去查询上报情况*/
                 List<String> unRemoveIds = jdbcTemplate.queryForList("SELECT wbs_id from u_information_query WHERE wbs_id in (" + wbsIds + ") and is_deleted = 0 and status in (1,2) GROUP BY wbs_id HAVING count(1) > 0", String.class);
-                if (!unRemoveIds.isEmpty()) {
-                    // 剔除此节点
-                    Map<String, String> map = unRemoveIds.stream().collect(Collectors.toMap(id -> id, Function.identity()));
-                    removeNodeList.removeIf(node -> {
-                        //删除掉表格 TODO(不清楚为什么要剔除表格,按理说删除节点后,节点下的表也应该一起删除的,猜测或许是为了方便恢复节点的时候表数据还存在)2023年9月19日
-                        boolean removeIf = node.getType() != null && new Integer("2").equals(node.getType());
-                        boolean equals = map.containsKey(node.getPKeyId().toString());
-                        if (equals) {
-                            unremoveNodeMap.put(node.getPKeyId(), node);
-                        }
-                        return removeIf || equals;
-                    });
-                    Map<Long, WbsTreeContract> contractMap = removeNodeList.stream().collect(Collectors.toMap(WbsTreeContract::getId, Function.identity()));
-                    Map<Long, WbsTreeContract> tempMap = new HashMap<>();
-                    unremoveNodeMap.forEach((key, value) -> collectNodeAndAncestors(value, contractMap, tempMap));
-                    unremoveNodeMap.putAll(tempMap);
-                }
+                // 剔除此节点
+                Map<String, String> map = unRemoveIds.stream().collect(Collectors.toMap(id -> id, Function.identity()));
+                removeNodeList.removeIf(node -> {
+                    //删除掉表格 TODO(不清楚为什么要剔除表格,按理说删除节点后,节点下的表也应该一起删除的,猜测或许是为了方便恢复节点的时候表数据还存在)2023年9月19日
+                    boolean removeIf = node.getType() != null && new Integer("2").equals(node.getType());
+                    boolean equals = map.containsKey(node.getPKeyId().toString());
+                    if (equals) {
+                        unremoveNodeMap.put(node.getPKeyId(), node);
+                    }
+                    return removeIf || equals;
+                });
+                Map<Long, WbsTreeContract> contractMap = removeNodeList.stream().collect(Collectors.toMap(WbsTreeContract::getId, Function.identity()));
+                Map<Long, WbsTreeContract> tempMap = new HashMap<>();
+                unremoveNodeMap.forEach((key, value) -> collectNodeAndAncestors(value, contractMap, tempMap));
+                unremoveNodeMap.putAll(tempMap);
             }
             if(removeNodeList.isEmpty()) {
                 return R.fail("删除失败,该节点下有已填报的资料");
@@ -3685,6 +3752,7 @@ public R removeContractTreeNodeJudge(@RequestParam String ids) {
             this.recycleBinService.save(new RecycleBin(String.join(",", idArray), "工程划分批量删除", 2, positionStr, projectId, contractId));
             //改为物理删除 (8.28改为逻辑删除,方便恢复)
             this.wbsTreeContractClient.removeContractTreeNode(idArray);
+            this.recycleBinInfoService.saveRecycleBinInfoByWbsTreeContract(String.join(",", idArray),ids);
             //更新redis
             this.informationQueryService.delAsyncWbsTree(removeWbsTreeContracts.get(0).getContractId());
             this.wbsTreeContractStatisticsClient.delWbsTreeContractNodes(String.join(",", idArray));
@@ -5211,4 +5279,42 @@ public R<Object> customAddContractNode(@RequestBody CustomAddContractNodeDTO dto
         }
         throw new IllegalArgumentException("新数据中未找到根节点");
     }
+
+    // pdf 检查任务添加
+    /**
+     * 首件wbs 树
+     *
+     * @return 结果
+     */
+    @GetMapping("/updateCheckPdfInfo")
+    @ApiOperationSupport(order = 40)
+    @ApiOperation(value = "添加pdf检查接口")
+    @ApiImplicitParams(value = {
+            @ApiImplicitParam(name = "type", value = "1:节点添加 2:文件添加",required = true),
+            @ApiImplicitParam(name = "classify", value = "1施工2监理",required = true),
+            @ApiImplicitParam(name = "ids", value = "多个用,拼接", required = true)
+    })
+    public  R updateCheckPdfInfo(@RequestParam String type, @RequestParam String ids,@RequestParam String classify) {
+
+        return informationQueryService.updateCheckPdfInfo(type, ids,classify);
+    }
+
+    /**
+     * 首件wbs 树
+     *
+     * @return 结果
+     */
+    @GetMapping("/getCheckPdfPaceInfo")
+    @ApiOperationSupport(order = 40)
+    @ApiOperation(value = "添加pdf检查接口")
+    @ApiImplicitParams(value = {
+            @ApiImplicitParam(name = "type", value = "1:节点添加 2:文件添加",required = true),
+            @ApiImplicitParam(name = "classify", value = "1施工2监理",required = true),
+            @ApiImplicitParam(name = "ids", value = "多个用,拼接", required = true)
+    })
+    public  R<ChekPdfPaceVo> getCheckPdfPaceInfo(@RequestParam String contractId,@RequestParam String classify) {
+
+        ChekPdfPaceVo checkPdfPaceInfo = informationQueryService.getCheckPdfPaceInfo(contractId, classify);
+        return R.data(checkPdfPaceInfo);
+    }
 }

+ 11 - 4
blade-service/blade-business/src/main/java/org/springblade/business/controller/MaterialProgressController.java

@@ -524,22 +524,22 @@ public class MaterialProgressController extends BladeController {
         //工序资料
         long processAmount = 0L;
         if (process.size() > 0) {
-            processAmount = this.informationQueryService.count(Wrappers.<InformationQuery>lambdaQuery().in(InformationQuery::getWbsId, process).eq(InformationQuery::getClassify, classifyType));
+            processAmount = this.informationQueryService.count(Wrappers.<InformationQuery>query().select("distinct wbs_id").in("wbs_id", process).eq("classify", classifyType));
         }
         //开工报告
         long workStartReportsAmount = 0L;
         if (workStartReports.size() > 0) {
-            workStartReportsAmount = this.informationQueryService.count(Wrappers.<InformationQuery>lambdaQuery().in(InformationQuery::getWbsId, workStartReports).eq(InformationQuery::getClassify, classifyType));
+            workStartReportsAmount = this.informationQueryService.count(Wrappers.<InformationQuery>query().select("distinct wbs_id").in("wbs_id", workStartReports).eq("classify", classifyType));
         }
         //质量评定
         long evaluationAmount = 0L;
         if (evaluation.size() > 0) {
-            evaluationAmount = this.informationQueryService.count(Wrappers.<InformationQuery>lambdaQuery().in(InformationQuery::getWbsId, evaluation).eq(InformationQuery::getClassify, classifyType));
+            evaluationAmount = this.informationQueryService.count(Wrappers.<InformationQuery>query().select("distinct wbs_id").in("wbs_id", evaluation).eq("classify", classifyType));
         }
         //中间交工
         long completionAmount = 0L;
         if (completion.size() > 0) {
-            completionAmount = this.informationQueryService.count(Wrappers.<InformationQuery>lambdaQuery().in(InformationQuery::getWbsId, completion).eq(InformationQuery::getClassify, classifyType));
+            completionAmount = this.informationQueryService.count(Wrappers.<InformationQuery>query().select("distinct wbs_id").in("wbs_id", completion).eq("classify", classifyType));
         }
 
         reVO.setProcessMaterialList("开工报告", workStartReports.size(), workStartReportsAmount);
@@ -556,6 +556,13 @@ public class MaterialProgressController extends BladeController {
         AtomicInteger await = new AtomicInteger();
         //已审批
         AtomicInteger approval = new AtomicInteger();
+        if (list != null && !list.isEmpty()) {
+            Map<Long, InformationQuery> map = list.stream().collect(Collectors.toMap(InformationQuery::getWbsId, item -> item, (v1, v2) -> v1.getId() > v2.getId() ? v1 : v2));
+            list = new ArrayList<>(map.values());
+        }
+        if (list ==  null) {
+            list = new ArrayList<>();
+        }
         list.forEach(vo -> {
             switch (vo.getStatus()) {
                 case 1:

+ 2 - 2
blade-service/blade-business/src/main/java/org/springblade/business/controller/NeiWaiYeProgressController.java

@@ -99,7 +99,7 @@ public class NeiWaiYeProgressController {
                 queryProcessDataVOList = this.informationQueryService.queryProcessDataByParentIdAndContractId2(node.getId().toString(), classFy, contractId);
             } else {
                 //填报节点
-                queryProcessDataVOList = this.informationQueryService.queryProcessDataByPrimaryKeyIdAndClassify(node.getPKeyId().toString(), classFy);
+                queryProcessDataVOList = this.informationQueryService.queryProcessDataByPrimaryKeyIdAndClassify(node.getPKeyId().toString(), classFy, null);
                 childList.clear();
                 //设置填报节点进集合中
                 childList.add(node);
@@ -165,7 +165,7 @@ public class NeiWaiYeProgressController {
                 queryProcessDataVOList = this.informationQueryService.queryProcessDataByParentIdAndContractId(node.getId().toString(), 1, contractId);
             } else {
                 //填报节点
-                queryProcessDataVOList = this.informationQueryService.queryProcessDataByPrimaryKeyIdAndClassify(node.getPKeyId().toString(), 1);
+                queryProcessDataVOList = this.informationQueryService.queryProcessDataByPrimaryKeyIdAndClassify(node.getPKeyId().toString(), 1, null);
                 childList.clear();
                 //设置填报节点进集合中
                 childList.add(node);

+ 94 - 10
blade-service/blade-business/src/main/java/org/springblade/business/controller/NeiYeController.java

@@ -1,6 +1,8 @@
 package org.springblade.business.controller;
 
 import cn.hutool.core.date.DateUtil;
+import com.aliyun.oss.ServiceException;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.core.toolkit.BeanUtils;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
@@ -24,9 +26,11 @@ import org.springblade.business.vo.NeiYeQueryVO;
 import org.springblade.business.vo.QueryProcessDataVO;
 import org.springblade.common.utils.CommonUtil;
 import org.springblade.common.utils.SnowFlakeUtil;
+import org.springblade.core.excel.util.ExcelUtil;
 import org.springblade.core.mp.support.Condition;
 import org.springblade.core.tool.api.R;
 import org.springblade.core.tool.utils.BeanUtil;
+import org.springblade.core.tool.utils.CollectionUtil;
 import org.springblade.core.tool.utils.ObjectUtil;
 import org.springblade.manager.entity.ContractInfo;
 import org.springblade.manager.entity.WbsFormElement;
@@ -36,6 +40,8 @@ import org.springblade.manager.feign.ContractClient;
 import org.springblade.manager.feign.WbsTreeContractClient;
 import org.springblade.manager.feign.WbsTreePrivateClient;
 import org.springblade.manager.vo.WbsTreeContractTreeVOS;
+import org.springblade.system.entity.DictBiz;
+import org.springblade.system.entity.Region;
 import org.springframework.core.io.ByteArrayResource;
 import org.springframework.core.io.Resource;
 import org.springframework.http.HttpHeaders;
@@ -46,6 +52,7 @@ import org.springframework.jdbc.core.JdbcTemplate;
 import org.springframework.jdbc.core.SingleColumnRowMapper;
 import org.springframework.web.bind.annotation.*;
 import org.springblade.core.mp.support.Query;
+import springfox.documentation.annotations.ApiIgnore;
 
 import javax.servlet.http.HttpServletResponse;
 import java.io.ByteArrayOutputStream;
@@ -86,6 +93,12 @@ public class NeiYeController {
     @ApiOperation(value = "获取内业台账列表")
     public R<IPage<NeiYeLedgerVO>> queryCurrentNodeNeiYeLedger(@RequestBody NeiYeQueryVO queryVO) {
         if (queryVO.getWbsIds() != null && queryVO.getWbsIds().size() > 0) {
+            //查询字典 dict_biz  code = table_file_type
+            List<DictBiz> dictBiz = jdbcTemplate.query("select * from blade_dict_biz where code = 'table_file_type'", new BeanPropertyRowMapper<>(DictBiz.class));
+            if(CollectionUtil.isEmpty(dictBiz)){
+               throw new ServiceException("table_file_type 字典未查询到数据");
+            }
+            Map<String, String> dictMap = dictBiz.stream().collect(Collectors.toMap(DictBiz::getDictKey, DictBiz::getDictValue));
             //生成列表
             List<NeiYeLedgerVO> neiYeLedgerVOList = new ArrayList<>();
             Integer contractType = 1;
@@ -112,18 +125,21 @@ public class NeiYeController {
             }
             //不是工序,则查询当前节点下的所有填报节点
             List<QueryProcessDataVO> queryDataResult;
+            //本身就是工序节点就查本节点
+            if(node.getNodeType() == 6){
+                queryVO.setSelectType(2);
+            }
             //有些填报节点的MajorDataType为0
-            if (!new Integer("6").equals(node.getNodeType()) && ObjectUtil.isNotEmpty(node.getMajorDataType()) &&!Arrays.asList("1,2,3,4".split(",")).contains(node.getMajorDataType().toString())
-                    && !node.getNodeName().contains("开工报告") && !node.getNodeName().contains("质量检验评定表")) {
+            if (queryVO.getSelectType() != null && queryVO.getSelectType() == 1) {
                 //非填报节点
                 if (node.getParentId() == 0) {
-                    queryDataResult = this.informationQueryService.queryProcessDataByParentIdAndContractIdTwo("", contractType, contractId);
+                    queryDataResult = this.informationQueryService.queryProcessDataByParentIdAndContractIdTwo("", contractType, contractId, queryVO.getDateIsComplete());
                 } else {
-                    queryDataResult = this.informationQueryService.queryProcessDataByParentIdAndContractIdTwo(node.getPKeyId().toString(), contractType, contractId);
+                    queryDataResult = this.informationQueryService.queryProcessDataByParentIdAndContractIdTwo(node.getAncestorsPId() + "," + node.getPKeyId(), contractType, contractId, queryVO.getDateIsComplete());
                 }
             } else {
                 //填报节点
-                queryDataResult = this.informationQueryService.queryProcessDataByPrimaryKeyIdAndClassify(node.getPKeyId().toString(), contractType);
+                queryDataResult = this.informationQueryService.queryProcessDataByPrimaryKeyIdAndClassify(node.getPKeyId().toString(), contractType, queryVO.getDateIsComplete());
             }
 
             if (queryDataResult != null && queryDataResult.size() > 0) {
@@ -134,6 +150,43 @@ public class NeiYeController {
                 List<String> stringList = jdbcTemplate.queryForList(sql, String.class);
                 if (stringList.size() > 0) {
                     queryDataResult.stream().forEach(qdr -> {
+                        StringBuilder sb = new StringBuilder();
+                        if (StringUtils.isEmpty(qdr.getPrivateTableFileType())) {
+                            sb.append("/");
+                        } else {
+                            //后台节点配置的附件类型
+                            List<String> privateFileType = Arrays.asList(qdr.getPrivateTableFileType().split(","));
+                            //附件名称
+                            List<String> names = new ArrayList<>();
+
+                            if (StringUtils.isNotEmpty(qdr.getContractTableFileType()) || StringUtils.isNotEmpty(qdr.getContractTableFileTypeTwo())) {
+                                if(StringUtils.isEmpty(qdr.getContractTableFileType())){
+                                    qdr.setContractTableFileType(qdr.getContractTableFileTypeTwo());
+                                } else {
+                                    qdr.setContractTableFileType(qdr.getContractTableFileType()+","+qdr.getContractTableFileTypeTwo());
+                                }
+
+                                List<String> contractFileType = Arrays.asList(qdr.getContractTableFileType().split(","));
+
+                                HashSet<String> strings = new HashSet<>(contractFileType);
+                                //后台配置的与合同段配置的附件类型比较 查到质检未配置的附件名称
+                                List<String> collect = privateFileType.stream().filter(fileType -> !strings.contains(fileType)).collect(Collectors.toList());
+                                if (CollectionUtil.isNotEmpty(collect)) {
+                                    collect.forEach(f -> names.add("【" + dictMap.get(f) + "】"));
+                                } else {
+                                    sb.append("报告完整");
+                                    qdr.setFileType(true);
+                                }
+                            } else {
+                                privateFileType.forEach(f -> names.add("【" + dictMap.get(f) + "】"));
+                            }
+                            if(CollectionUtil.isNotEmpty(names)){
+                                sb.append("缺少").append(StringUtils.join(names, "、"));
+                            }
+                        }
+
+                        qdr.setFileTypeMsg(sb.toString());
+
                         if (stringList.contains(qdr.getPrimaryKeyId())) {
                             qdr.setIsExperiment("true");
                         }
@@ -145,6 +198,10 @@ public class NeiYeController {
                     queryDataResult = queryDataResult.stream()
                             .filter(qdr -> isExperiment.equals(qdr.getIsExperiment())).collect(Collectors.toList());
                 }
+                //过滤附件
+                if (queryVO.getIsFile() != null) {
+                    queryDataResult = queryDataResult.stream().filter(f -> Objects.equals(f.getFileType(), queryVO.getIsFile())).collect(Collectors.toList());
+                }
                 //设置评定值
                 queryDataResult.stream().forEach(qdr -> qdr.setEvaluate("false"));
                 List<QueryProcessDataVO> vos = queryDataResult.stream().filter(qdr -> qdr.getTitle().contains("质量检验评定表"))
@@ -240,8 +297,13 @@ public class NeiYeController {
                     return R.data(300, null, "未查询到数据");
                 }
                 //分组
-                List<List<QueryProcessDataVO>> groupList = CommonUtil.getBatchSize(queryDataResult, queryVO.getSize());
-                List<QueryProcessDataVO> groupQueryList = groupList.get(queryVO.getCurrent() == 0 ? 0 : queryVO.getCurrent() - 1);
+                List<QueryProcessDataVO> groupQueryList = null;
+                if(queryVO.getSize() != null && queryVO.getSize() > 0){
+                    List<List<QueryProcessDataVO>> groupList = CommonUtil.getBatchSize(queryDataResult, queryVO.getSize());
+                     groupQueryList = groupList.get(queryVO.getCurrent() == 0 ? 0 : queryVO.getCurrent() - 1);
+                }else{
+                    groupQueryList = queryDataResult;
+                }
 
                 //获取所有施工日志记录
                 List<String> primaryKeyIds = groupQueryList.stream().map(QueryProcessDataVO::getPrimaryKeyId).distinct().collect(Collectors.toList());
@@ -273,7 +335,7 @@ public class NeiYeController {
                     }
                     //todo 当前缺少是否关联评定、是否关联试验 =================================
                     //新增列表数据
-                    neiYeLedgerVOList.add(new NeiYeLedgerVO(map.get("unitProject"),
+                    NeiYeLedgerVO neiYeLedgerVO = new NeiYeLedgerVO(map.get("unitProject"),
                             map.get("partProject"),
                             map.get("partChildProject"),
                             map.get("subentryProject"),
@@ -285,8 +347,13 @@ public class NeiYeController {
                             vo.getEvaluate(),
                             vo.getIsExperiment(),
                             vo.getReportNumber(),
-                            vo.getInformationQueryId())
-                    );
+                            vo.getInformationQueryId());
+
+                    neiYeLedgerVO.setDateIsComplete(vo.getDateIsComplete());
+                    neiYeLedgerVO.setInfoQueryName(vo.getInfoQueryName());
+                    neiYeLedgerVO.setPdfUrl(vo.getPdfUrl());
+                    neiYeLedgerVO.setFileTypeMsg(vo.getFileTypeMsg());
+                    neiYeLedgerVOList.add(neiYeLedgerVO);
                 }
                 //转换为page信息
                 Query query = new Query();
@@ -552,4 +619,21 @@ public class NeiYeController {
         }
     }
 
+
+    /**
+     * 导出业内台账
+     */
+    @PostMapping("export")
+    @ApiOperationSupport(order = 11)
+    @ApiOperation(value = "导出业内台账", notes = "传入user")
+    public void exportRegion(@RequestBody NeiYeQueryVO queryVO,HttpServletResponse response) {
+        //导出所有
+        queryVO.setSize(-1);
+        R<IPage<NeiYeLedgerVO>> iPageR = queryCurrentNodeNeiYeLedger(queryVO);
+        //获取数据
+        if(iPageR.isSuccess()){
+            List<NeiYeLedgerVO> list = iPageR.getData().getRecords();
+            ExcelUtil.export(response, "内业台账" + org.springblade.core.tool.utils.DateUtil.time(), "行政区划数据表", list, NeiYeLedgerVO.class);
+        }
+    }
 }

+ 110 - 0
blade-service/blade-business/src/main/java/org/springblade/business/controller/RecycleBinController.java

@@ -10,25 +10,37 @@ import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
 import lombok.AllArgsConstructor;
 
 import org.apache.commons.lang.StringUtils;
+import org.springblade.business.dto.RecycleBinInfoDTO;
 import org.springblade.business.entity.ArchiveFile;
 import org.springblade.business.entity.ImageClassificationFile;
+import org.springblade.business.entity.RecycleBinInfo;
 import org.springblade.business.feign.InformationQueryClient;
 import org.springblade.business.feignClient.WbsTreeContractStatisticsClientImpl;
 import org.springblade.business.service.IArchiveFileService;
 import org.springblade.business.service.IImageClassificationFileService;
+import org.springblade.business.service.IRecycleBinInfoService;
+import org.springblade.business.vo.RecycleBinInfoVO;
 import org.springblade.business.vo.RecycleBinVO;
 import org.springblade.core.mp.support.Condition;
 import org.springblade.core.mp.support.Query;
+import org.springblade.core.redis.cache.BladeRedis;
 import org.springblade.core.secure.utils.AuthUtil;
 import org.springblade.core.tool.api.R;
 import org.springblade.core.tool.utils.DateUtil;
+import org.springblade.core.tool.utils.ObjectUtil;
+import org.springblade.core.tool.utils.StringUtil;
+import org.springblade.manager.entity.WbsTreeContract;
 import org.springblade.manager.feign.WbsTreeContractClient;
+import org.springblade.system.user.vo.UserVO2;
+import org.springframework.jdbc.core.BeanPropertyRowMapper;
+import org.springframework.jdbc.core.JdbcTemplate;
 import org.springframework.web.bind.annotation.*;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import org.springblade.business.entity.RecycleBin;
 import org.springblade.business.service.IRecycleBinService;
 import org.springblade.core.boot.ctrl.BladeController;
 
+import javax.validation.Valid;
 import java.util.*;
 import java.util.stream.Collectors;
 
@@ -55,6 +67,9 @@ public class RecycleBinController extends BladeController {
     private final InformationQueryClient informationQueryClient;
 
     private final WbsTreeContractStatisticsClientImpl wbsTreeContractStatisticsClient;
+    private final IRecycleBinInfoService recycleBinInfoService;
+    private final BladeRedis bladeRedis;
+    private final JdbcTemplate jdbcTemplate;
 
     /**
      * 恢复
@@ -168,4 +183,99 @@ public class RecycleBinController extends BladeController {
         return R.data(this.recycleBinService.page(Condition.getPage(query), wrapper));
     }
 
+    @GetMapping("/page")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "分页")
+    public R<IPage<RecycleBinInfo>> page(@Valid RecycleBinInfoVO vo) {
+        return R.data(this.recycleBinInfoService.selectPage(vo));
+    }
+
+    /**
+     * 恢复
+     */
+    @PostMapping("/recover")
+    @ApiOperationSupport(order = 2)
+    @ApiOperation(value = "恢复(工程划分)")
+    public R<Boolean> recover(@RequestBody RecycleBinInfoDTO dto) {
+        if (StringUtil.hasText(dto.getIds())) {
+            //获取数据
+            String[] ids = dto.getIds().split(",");
+            List<Long> collect = Arrays.stream(ids).filter(StringUtils::isNumeric).map(Long::parseLong).collect(Collectors.toList());
+            if (collect.isEmpty()) {
+                return R.data(true);
+            }
+            List<RecycleBinInfo> recycleBinInfoList = this.recycleBinInfoService.list(Wrappers.<RecycleBinInfo>lambdaQuery().in(RecycleBinInfo::getId, collect).eq(RecycleBinInfo::getStatus, 0).eq(RecycleBinInfo::getDelType, 2));
+            if (dto.getRecoverOperationData() == 1) {
+                Set<Long> set = recycleBinInfoList.stream().map(RecycleBinInfo::getDelRootId).collect(Collectors.toSet());
+                recycleBinInfoList = this.recycleBinInfoService.list(Wrappers.<RecycleBinInfo>lambdaQuery().in(RecycleBinInfo::getDelRootId, set)
+                                .eq(RecycleBinInfo::getDelType, 2).eq(RecycleBinInfo::getStatus, 0));
+            }
+            boolean regainNode = false;
+            if (!recycleBinInfoList.isEmpty()) {
+                List<String> processNodeList = new ArrayList<>();
+                try {
+                    //恢复数据
+                    Set<Long> parentIds = new HashSet<>();
+                    for (RecycleBinInfo info : recycleBinInfoList) {
+                        String position = info.getBusinessId();
+                        if (position ==  null) {
+                            continue;
+                        }
+                        String[] split = position.split(",");
+                        for (String s : split) {
+                            if (StringUtil.isNumeric(s) && !s.equals("0")) {
+                                parentIds.add(Long.parseLong(s));
+                            }
+                        }
+                    }
+                    if (!parentIds.isEmpty()) {
+                        List<RecycleBinInfo> list = this.recycleBinInfoService.list(Wrappers.<RecycleBinInfo>lambdaQuery().in(RecycleBinInfo::getDelId, parentIds).eq(RecycleBinInfo::getDelType, 2).eq(RecycleBinInfo::getStatus, 0));
+                        recycleBinInfoList.addAll(list);
+                    }
+                    processNodeList = recycleBinInfoList.stream().map(item -> item.getDelId() + "").collect(Collectors.toList());
+                    regainNode = this.wbsTreeContractClient.regainRemoveTreeByPrimaryKeyIds(processNodeList);
+                    List<WbsTreeContract> query = jdbcTemplate.query("SELECT p_key_id  FROM m_wbs_tree_contract a WHERE  ( SELECT count(1) FROM m_wbs_tree_contract WHERE contract_id = a.contract_id and type = 1 AND p_id = a.p_id AND full_name = a.full_name AND p_key_id != a.p_key_id AND is_deleted = 0 ) > 0 " +
+                            "AND is_deleted = 0 and a.p_key_id in ( " + String.join(",", processNodeList) + ")", new BeanPropertyRowMapper<>(WbsTreeContract.class));
+                    if (!query.isEmpty()) {
+                        String collect1 = query.stream().map(item -> item.getPKeyId() + "").collect(Collectors.joining(","));
+                        jdbcTemplate.execute("update m_wbs_tree_contract set full_name = CONCAT( full_name, '(恢)' ) where p_key_id in (" + collect1 + ")");
+                    }
+                } catch (Exception e) {
+                    e.printStackTrace();
+                }
+                informationQueryClient.delAsyncWbsTree(recycleBinInfoList.get(0).getContractId() + "");
+                wbsTreeContractStatisticsClient.recycleWbsTreeContractNodes(String.join(",", processNodeList));
+            }
+            //删除回收站记录
+            if (!recycleBinInfoList.isEmpty() && regainNode) {
+                List<Long> recycleBinIds = recycleBinInfoList.stream().map(RecycleBinInfo::getId).collect(Collectors.toList());
+                this.recycleBinInfoService.update(Wrappers.<RecycleBinInfo>lambdaUpdate().set(RecycleBinInfo::getStatus, 1).set(RecycleBinInfo::getUpdateTime, new Date())
+                        .set(RecycleBinInfo::getUpdateUser, AuthUtil.getUserId()).set(RecycleBinInfo::getUpdateUserName, AuthUtil.getNickName()).in(RecycleBinInfo::getId, recycleBinIds));
+                Set<Long> set = recycleBinInfoList.stream().map(RecycleBinInfo::getContractId).collect(Collectors.toSet());
+                for (Long l : set) {
+                    bladeRedis.del("blade:recycle:user:cache:" + l, "blade:recycle:user:cache:" + l + "_1");
+                }
+                return R.data(true);
+            } else {
+                return R.data(300, false, "数据恢复失败,请联系维护人员处理");
+            }
+        }
+        return R.data(300, false, "未找到需要需要恢复的数据");
+    }
+
+    @GetMapping("/queryUser")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "查询用户")
+    public R<Collection<UserVO2>> queryUser(@RequestParam Long contractId, @RequestParam(required = false, defaultValue = "0") Integer isRecycleBin, @RequestParam(required = false) String name) {
+        return R.data(this.recycleBinInfoService.queryUser(contractId,isRecycleBin, name));
+    }
+
+
+    @GetMapping("/queryOperation")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "查询同一批删除数据")
+    public R<Collection<RecycleBinInfo>> queryOperation(@RequestParam String ids) {
+        return R.data(this.recycleBinInfoService.queryOperation(ids));
+    }
+
 }

+ 29 - 6
blade-service/blade-business/src/main/java/org/springblade/business/controller/TaskController.java

@@ -52,6 +52,7 @@ import org.springblade.manager.dto.SaveUserInfoByProjectDTO;
 import org.springblade.manager.entity.ContractInfo;
 import org.springblade.manager.entity.ContractRelationJlyz;
 import org.springblade.manager.entity.ProjectInfo;
+import org.springblade.manager.feign.ProjectClient;
 import org.springblade.resource.feign.CommonFileClient;
 import org.springblade.resource.feign.NewISmsClient;
 import org.springblade.system.cache.ParamCache;
@@ -103,6 +104,7 @@ public class TaskController extends BladeController {
     private final ArchiveExpertConclusionClient conclusionClient;
     private final MessageWarningServiceImpl messageWarningServiceImpl;
     private final OperationLogClient operationLogClient;
+    private final ProjectClient projectClient;
 
     /**
      * 记录短信验证码超时时间
@@ -110,18 +112,23 @@ public class TaskController extends BladeController {
     @GetMapping("/save-sms-timeout")
     @ApiOperationSupport(order = 13)
     @ApiOperation(value = "记录短信验证码超时时间")
-    public void saveSmsTimeout(@RequestParam String code) {
+    public void saveSmsTimeout(@RequestParam String code,String projectId) {
         //获取账户记录
      ///   String aesKey = "O2BEeIv399qHQNhD6aGW8R8DEj4bqHXm";
      //   String accode = AesUtil.decryptFormBase64ToString(code, aesKey);
         DefaultConfig config = this.defaultConfigService.getOne(Wrappers.<DefaultConfig>lambdaQuery()
                 .eq(DefaultConfig::getCreateUser, AuthUtil.getUserId())
                 .isNotNull(DefaultConfig::getSmsCode));
+        int addTime = 1;
         if (config != null) {
+            if(projectId!=null && !projectId.equals("") && Func.isNotEmpty(projectId)){
+                ProjectInfo projectInfo = projectClient.getById(projectId);
+                addTime = projectInfo.getMsTime();
+            }
             //获取当前时间
             Date now = DateUtil.now();
             // 16 改为 1小时后超时
-            now = DateUtil.plusHours(now, 1);
+            now = DateUtil.plusHours(now, addTime);
 
             LambdaUpdateWrapper<DefaultConfig> wrapper = new LambdaUpdateWrapper<>();
             wrapper.set(DefaultConfig::getSmsTimeOut, DateUtil.format(now, "yyyy-MM-dd HH:mm:ss"));
@@ -165,20 +172,25 @@ public class TaskController extends BladeController {
     /**
      * 批量审批详情
      */
-    @GetMapping("/batch-approval-parameter")
+    @PostMapping("/batch-approval-parameter")
     @ApiOperationSupport(order = 11)
     @ApiOperation(value = "批量页详情")
     @ApiImplicitParams({
             @ApiImplicitParam(name = "formDataId", value = "数据源", required = true),
             @ApiImplicitParam(name = "approvalType", value = "上报类型", required = true)
     })
-    public R<List<TaskApprovalVO>> getBatchApprovalTaskParameter(@RequestParam String formDataId, @RequestParam Integer approvalType) {
+    public R<List<TaskApprovalVO>> getBatchApprovalTaskParameter(@RequestBody BatchTaskVO vo) {
+        String formDataId = vo.getFormDataId();
+        String approvalType = vo.getApprovalType();
         List<String> longs = Func.toStrList(formDataId);
+        List<String> apptype = Func.toStrList(approvalType);
         List<TaskApprovalVO> taskApprovalVOList = new ArrayList<>();
-        for (String aLong : longs) {
+        for (int i=0;i<longs.size();i++) {
+            String aLong = longs.get(i);
+            Integer approv = Integer.parseInt(apptype.get(i));
             TaskApprovalVO result = new TaskApprovalVO();
             result.setFormDataId(aLong);
-            result.setApprovalType(approvalType);
+            result.setApprovalType(approv);
             taskApprovalVOList.add(this.taskService.queryBusinessData(result));
         }
         return R.data(taskApprovalVOList);
@@ -2217,4 +2229,15 @@ public class TaskController extends BladeController {
         return R.data(true);
     }
 
+    /**
+     * 资料填报-任务管理- 电签签字
+     */
+    @PostMapping("/reSigningEVisaByUserIds")
+    @ApiOperationSupport(order = 3)
+    @ApiOperation(value = "任务管理-一键重签", notes = "传入taskIds、下拉框的contractId、projectId")
+    public R<Object> reSigningEVisaByUserIds(@RequestParam String ids, @RequestParam String userIds) {
+
+       return taskService.reSigningEVisaByUserIds(ids,userIds);
+    }
+
 }

+ 207 - 0
blade-service/blade-business/src/main/java/org/springblade/business/controller/TrialClassificationTreeController.java

@@ -0,0 +1,207 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import io.swagger.annotations.ApiParam;
+import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
+import lombok.AllArgsConstructor;
+import javax.validation.Valid;
+
+import org.springblade.business.dto.TrialClassificationTreeDTO;
+import org.springblade.business.dto.TrialClassificationTreeDTO1;
+import org.springblade.common.utils.SnowFlakeUtil;
+import org.springblade.core.log.exception.ServiceException;
+import org.springblade.core.mp.support.Condition;
+import org.springblade.core.mp.support.Query;
+import org.springblade.core.tool.api.R;
+import org.springblade.core.tool.utils.BeanUtil;
+import org.springblade.core.tool.utils.Func;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.bind.annotation.RequestParam;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import org.springblade.business.entity.TrialClassificationTree;
+import org.springblade.business.vo.TrialClassificationTreeVO;
+import org.springblade.business.service.ITrialClassificationTreeService;
+import org.springblade.core.boot.ctrl.BladeController;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.stream.Collectors;
+
+/**
+ * 德飞试验系统检测分类树 控制器
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@RestController
+@AllArgsConstructor
+@RequestMapping("/trialclassificationtree")
+@Api(value = "德飞试验系统检测分类树", tags = "德飞试验系统检测分类树接口")
+public class TrialClassificationTreeController extends BladeController {
+
+	private final ITrialClassificationTreeService trialClassificationTreeService;
+
+//	/**
+//	 * 详情
+//	 */
+//	@GetMapping("/detail")
+//	@ApiOperationSupport(order = 1)
+//	@ApiOperation(value = "详情", notes = "传入trialClassificationTree")
+//	public R<TrialClassificationTree> detail(TrialClassificationTree trialClassificationTree) {
+//		TrialClassificationTree detail = trialClassificationTreeService.getOne(Condition.getQueryWrapper(trialClassificationTree));
+//		return R.data(detail);
+//	}
+//
+	/**
+	 * 德飞试验系统检测分类树
+	 */
+	@GetMapping("/list")
+	@ApiOperationSupport(order = 2)
+	@ApiOperation(value = "查询当前节点的子节点", notes = "传入trialClassificationTree")
+	public R<List<TrialClassificationTreeVO>> list(Long id,Long projectId) {
+		if(projectId==null){
+			throw new ServiceException("请选择项目");
+		}
+		List<TrialClassificationTreeVO> list = trialClassificationTreeService.selectAllNode(id,projectId);
+		return R.data(list);
+	}
+
+//	/**
+//	 * 自定义分页 德飞试验系统检测分类树
+//	 */
+//	@GetMapping("/page")
+//	@ApiOperationSupport(order = 3)
+//	@ApiOperation(value = "分页", notes = "传入trialClassificationTree")
+//	public R<IPage<TrialClassificationTreeVO>> page(TrialClassificationTreeVO trialClassificationTree, Query query) {
+//		IPage<TrialClassificationTreeVO> pages = trialClassificationTreeService.selectTrialClassificationTreePage(Condition.getPage(query), trialClassificationTree);
+//		return R.data(pages);
+//	}
+
+	/**
+	 * 新增 德飞试验系统检测分类树
+	 */
+	@PostMapping("/save")
+	@ApiOperationSupport(order = 4)
+	@ApiOperation(value = "新增", notes = "传入trialClassificationTree")
+	public R save(@Valid @RequestBody TrialClassificationTreeDTO1 dto) {
+		Boolean flag=false;
+		if(dto.getGroupType()!=null&&dto.getGroupType()==1){
+			if(dto.getList().size()>1){
+				trialClassificationTreeService.deleteByGroupType(dto.getGroupType());
+				flag=true;
+			}
+		}
+		// 假设您有一个 List<TrialClassificationTreeDTO> list
+		Map<Long, Long> map = dto.getList().stream()
+				.collect(Collectors.toMap(
+						TrialClassificationTreeDTO::getId, // 按 parentId 分组
+						TrialClassificationTreeDTO::getParentId // 收集每个分组的 id 列表
+				));
+		List<TrialClassificationTree>insertList=new ArrayList<>();
+		for (TrialClassificationTreeDTO trialClassificationTreeDTO : dto.getList()) {
+			TrialClassificationTree trialClassificationTree = new TrialClassificationTree();
+			BeanUtil.copy(trialClassificationTreeDTO, trialClassificationTree);
+			Long parentId = trialClassificationTree.getParentId();
+			StringBuilder classificationAncestors = new StringBuilder();
+			classificationAncestors.append(trialClassificationTree.getId());
+			if(parentId!=0){
+				classificationAncestors.append( ",").append(parentId);
+			}
+			while (parentId!=null&&parentId!=0){
+				parentId = selectAncestors(parentId,map,flag);
+				if(parentId!=null&&parentId!=0){
+					classificationAncestors.append(",").append(parentId);
+				}
+			}
+			trialClassificationTree.setClassificationAncestors(classificationAncestors.toString());
+			trialClassificationTree.setGroupType(dto.getGroupType());
+			insertList.add(trialClassificationTree);
+		}
+		return R.status(trialClassificationTreeService.saveBatch(insertList));
+	}
+
+	public Long selectAncestors(Long parentId,Map<Long, Long> map,Boolean flag) {
+		if(parentId==0){
+			return null;
+		}
+		if(map.containsKey(parentId)){
+			if(map.get(parentId)!=null){
+				return map.get(parentId);
+			}
+		}else {
+			if(!flag){
+				return trialClassificationTreeService.selectAncestors(parentId);
+			}
+		}
+		return null;
+	}
+
+	/**
+	 * 修改 德飞试验系统检测分类树
+	 */
+	@PostMapping("/update")
+	@ApiOperationSupport(order = 5)
+	@ApiOperation(value = "修改", notes = "传入trialClassificationTree")
+	public R update(Long id,String classificationName) {
+		if(id==null){
+			return R.fail("请选择要修改的分类");
+		}
+		if(Func.isEmpty(classificationName)){
+			return R.fail("请输入分类名称");
+		}
+		TrialClassificationTree trialClassificationTree = new TrialClassificationTree();
+		trialClassificationTree.setClassificationName(classificationName);
+		return R.status(trialClassificationTreeService.update(new UpdateWrapper<TrialClassificationTree>().set("classification_name", classificationName).eq("id", id)));
+	}
+
+//	/**
+//	 * 新增或修改 德飞试验系统检测分类树
+//	 */
+//	@PostMapping("/submit")
+//	@ApiOperationSupport(order = 6)
+//	@ApiOperation(value = "新增或修改", notes = "传入trialClassificationTree")
+//	public R submit(@Valid @RequestBody List<TrialClassificationTree> trialClassificationTrees) {
+//		return R.status(trialClassificationTreeService.saveOrUpdateBatch(trialClassificationTrees));
+//	}
+
+	
+//	/**
+//	 * 删除 德飞试验系统检测分类树
+//	 */
+//	@PostMapping("/remove")
+//	@ApiOperationSupport(order = 7)
+//	@ApiOperation(value = "逻辑删除", notes = "传入ids")
+//	public R remove(@ApiParam(value = "主键集合", required = true) @RequestParam String ids) {
+//		return R.status(trialClassificationTreeService.deleteLogic(Func.toLongList(ids)));
+//	}
+
+
+	@PostMapping("/remove")
+	@ApiOperationSupport(order = 7)
+	@ApiOperation(value = "逻辑删除", notes = "传入id")
+	public R remove(@ApiParam(value = "主键集合", required = true) @RequestParam Long id) {
+		boolean update = trialClassificationTreeService.update(new UpdateWrapper<TrialClassificationTree>().set("is_deleted", 1).in("classification_ancestors", id));
+		return R.status(update);
+	}
+}

+ 100 - 0
blade-service/blade-business/src/main/java/org/springblade/business/controller/TrialCyController.java

@@ -0,0 +1,100 @@
+package org.springblade.business.controller;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiImplicitParam;
+import io.swagger.annotations.ApiImplicitParams;
+import io.swagger.annotations.ApiOperation;
+import lombok.AllArgsConstructor;
+import org.springblade.business.entity.TrialContainerClassification;
+import org.springblade.business.entity.TrialCyFinishTestReport;
+import org.springblade.business.entity.TrialCyTestType;
+import org.springblade.business.entity.TrialCyThirdReport;
+import org.springblade.business.service.TrialCyService;
+import org.springblade.business.service.TrialCyTestTypeService;
+import org.springblade.business.vo.ThirdReportVo;
+import org.springblade.business.vo.TrialCyThirdReportQueryVo;
+import org.springblade.core.tool.api.R;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestParam;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.List;
+
+/**
+ * 成渝试验数据接口
+ * @author LHB
+ */
+@RestController
+@AllArgsConstructor
+@RequestMapping("/cyTrial")
+@Api(value = "成渝试验数据接口", tags = "成渝试验数据接口")
+public class TrialCyController {
+
+    private TrialCyService trialCyService;
+
+
+    /**
+     * 根据合同段id验证当前合同段是否未成渝项目下未开启试验功能的合同段
+     * @return
+     */
+    @GetMapping("/isCyAndTestModule")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "验证是否使用成渝那边的树", notes = "传入合同段id")
+    public R<Boolean> isCyAndTestModule(Long projectId,Long contractId){
+        return R.data(trialCyService.isCyAndTestModule(projectId, contractId));
+    }
+
+    /**
+     * 获取成渝那边的树
+     * @return
+     */
+    @GetMapping("/getTree")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "获取成渝那边的树", notes = "传入项目id")
+    public R<List<TrialCyTestType>> getTree(Long projectId, String parentId){
+        return R.data(trialCyService.getTree(projectId,parentId));
+    }
+
+    /**
+     * 获取试验检测报告
+     * @return
+     */
+    @GetMapping("/getTrialDetectionReport")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "获取试验检测报告", notes = "")
+    public R<Page<ThirdReportVo>> getTrialDetectionReport(@Validated TrialCyThirdReportQueryVo queryVo){
+        return R.data(trialCyService.getTrialDetectionReport(queryVo));
+    }
+
+
+    /**
+     * 获取第三方/外委 检测报告
+     * @return
+     */
+    @GetMapping("/getThirdReport")
+    @ApiOperationSupport(order = 1)
+    @ApiOperation(value = "获取第三方/外委 检测报告", notes = "")
+    public R<Page<ThirdReportVo>> getThirdReport(@Validated TrialCyThirdReportQueryVo queryVo){
+        return R.data(trialCyService.getThirdReport(queryVo));
+    }
+
+
+    /**
+     * 清除成渝试验关联
+     * @return
+     */
+    @GetMapping("/clearTrialAssociation")
+    @ApiOperation(value = "清除成渝试验关联", notes = "")
+    @ApiImplicitParams(value = {
+            @ApiImplicitParam(name = "nodeId", value = "节点", required = true),
+            @ApiImplicitParam(name = "recordId", value = "pkeyId", required = true)
+    })
+    public R<Boolean> clearTrialAssociation(Long nodeId, Long recordId){
+        return R.data(trialCyService.clearTrialAssociation(nodeId,recordId));
+    }
+
+}

+ 166 - 0
blade-service/blade-business/src/main/java/org/springblade/business/controller/TrialSystemDockingController.java

@@ -0,0 +1,166 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.controller;
+
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import io.swagger.annotations.ApiParam;
+import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport;
+import lombok.AllArgsConstructor;
+import javax.validation.Valid;
+
+import org.apache.commons.lang.StringUtils;
+import org.springblade.business.dto.TrialSystemDockingDTO;
+import org.springblade.business.dto.TrialSystemDockingDTO1;
+import org.springblade.business.entity.TrialClassificationTree;
+import org.springblade.business.service.ITrialClassificationTreeService;
+import org.springblade.core.mp.support.Condition;
+import org.springblade.core.mp.support.Query;
+import org.springblade.core.tool.api.R;
+import org.springblade.core.tool.utils.BeanUtil;
+import org.springblade.core.tool.utils.Func;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.bind.annotation.RequestParam;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import org.springblade.business.entity.TrialSystemDocking;
+import org.springblade.business.vo.TrialSystemDockingVO;
+import org.springblade.business.service.ITrialSystemDockingService;
+import org.springblade.core.boot.ctrl.BladeController;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.stream.Collectors;
+
+/**
+ * 德飞试验系统对接表 控制器
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+@RestController
+@AllArgsConstructor
+@RequestMapping("/trialsystemdocking")
+@Api(value = "德飞试验系统对接表", tags = "德飞试验系统对接表接口")
+public class TrialSystemDockingController extends BladeController {
+
+	private final ITrialSystemDockingService trialSystemDockingService;
+
+	private final ITrialClassificationTreeService trialClassificationTreeService;
+
+
+	/**
+	 * 详情
+	 */
+	@GetMapping("/detail")
+	@ApiOperationSupport(order = 1)
+	@ApiOperation(value = "详情", notes = "传入trialSystemDocking")
+	public R<TrialSystemDocking> detail(@RequestParam Long id) {
+		TrialSystemDocking detail = trialSystemDockingService.getById(id);
+		return R.data(detail);
+	}
+
+//	/**
+//	 * 分页 德飞试验系统对接表
+//	 */
+//	@GetMapping("/list")
+//	@ApiOperationSupport(order = 2)
+//	@ApiOperation(value = "分页", notes = "传入trialSystemDocking")
+//	public R<IPage<TrialSystemDocking>> list(TrialSystemDocking trialSystemDocking, Query query) {
+//		IPage<TrialSystemDocking> pages = trialSystemDockingService.page(Condition.getPage(query), Condition.getQueryWrapper(trialSystemDocking));
+//		return R.data(pages);
+//	}
+
+	/**
+	 * 自定义分页 德飞试验系统对接表
+	 */
+	@GetMapping("/page")
+	@ApiOperationSupport(order = 3)
+	@ApiOperation(value = "分页", notes = "传入trialSystemDocking")
+	public R<IPage<TrialSystemDockingVO>> page(TrialSystemDockingVO trialSystemDocking, Query query) {
+		IPage<TrialSystemDockingVO> pages = trialSystemDockingService.selectTrialSystemDockingPage(Condition.getPage(query), trialSystemDocking);
+		return R.data(pages);
+	}
+
+	/**
+	 * 新增 德飞试验系统对接表
+	 */
+	@PostMapping("/save")
+	@ApiOperationSupport(order = 4)
+	@ApiOperation(value = "新增", notes = "传入trialSystemDocking")
+	public R save(@Valid @RequestBody List<TrialSystemDockingDTO> list) {
+		List<TrialSystemDocking>list1=new ArrayList<>();
+		for (TrialSystemDockingDTO trialSystemDockingDTO : list) {
+			TrialSystemDocking trialSystemDocking = new TrialSystemDocking();
+			BeanUtil.copy(trialSystemDockingDTO,trialSystemDocking);
+			TrialClassificationTree trialClassificationTree = trialClassificationTreeService.getById(trialSystemDockingDTO.getClassificationId());
+			if(trialClassificationTree!=null){
+				trialSystemDocking.setClassificationAncestors(trialClassificationTree.getClassificationAncestors());
+			}
+			list1.add(trialSystemDocking);
+		}
+		boolean b = trialSystemDockingService.saveBatch(list1);
+		if(b){
+			//异步下载文件并且上传Oss
+			trialSystemDockingService.syncUpdateFile(list1);
+		}
+		Map<Long, Long> map = list1.stream().collect(Collectors.toMap(TrialSystemDocking::getDataId, TrialSystemDocking::getId));
+		return R.data(map);
+	}
+
+	/**
+	 * 修改 德飞试验系统对接表
+	 */
+	@PostMapping("/update")
+	@ApiOperationSupport(order = 5)
+	@ApiOperation(value = "修改", notes = "传入trialSystemDocking")
+	public R update(@Valid @RequestBody TrialSystemDockingDTO1 trialSystemDockingDTO) {
+		TrialSystemDocking trialSystemDocking = trialSystemDockingService.getById(trialSystemDockingDTO.getId());
+		BeanUtil.copy(trialSystemDockingDTO,trialSystemDocking);
+		if(StringUtils.isNotEmpty(trialSystemDockingDTO.getFileUrl())&&!trialSystemDockingDTO.getFileUrl().equals(trialSystemDocking.getFileUrl())){
+			trialSystemDockingService.syncUpdateFile1(trialSystemDocking);
+		}
+		return R.status(trialSystemDockingService.updateById(trialSystemDocking));
+	}
+
+//	/*
+//	 * 新增或修改 德飞试验系统对接表
+//	 */
+//	@PostMapping("/submit")
+//	@ApiOperationSupport(order = 6)
+//	@ApiOperation(value = "新增或修改", notes = "传入trialSystemDocking")
+//	public R submit(@Valid @RequestBody TrialSystemDocking trialSystemDocking) {
+//		return R.status(trialSystemDockingService.saveOrUpdate(trialSystemDocking));
+//	}
+
+	
+	/**
+	 * 删除 德飞试验系统对接表
+	 */
+	@PostMapping("/remove")
+	@ApiOperationSupport(order = 7)
+	@ApiOperation(value = "逻辑删除", notes = "传入ids")
+	public R remove(@ApiParam(value = "主键集合", required = true) @RequestParam String ids) {
+		if (Func.isEmpty(ids)) {
+			return R.fail("参数错误");
+		}
+		trialSystemDockingService.updatedelete(Func.toLongList(ids));
+		return R.status(true);
+	}
+
+}

+ 103 - 0
blade-service/blade-business/src/main/java/org/springblade/business/feignClient/ArchiveFileClientImpl.java

@@ -8,7 +8,10 @@ import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
 import lombok.AllArgsConstructor;
 import org.apache.commons.lang.StringUtils;
+import org.springblade.archive.dto.FindAndReplaceDto;
+import org.springblade.archive.entity.ArchivesAuto;
 import org.springblade.archive.vo.ArchivesAutoVO;
+import org.springblade.business.dto.FindAndReplaceDto1;
 import org.springblade.business.entity.ArchiveFile;
 import org.springblade.business.feign.ArchiveFileClient;
 import org.springblade.business.mapper.ArchiveFileMapper;
@@ -16,6 +19,7 @@ import org.springblade.business.service.IArchiveFileService;
 import org.springblade.business.service.ITaskService;
 import org.springblade.business.vo.ArchiveFileVO;
 import org.springblade.common.utils.FileUtils;
+import org.springblade.core.log.exception.ServiceException;
 import org.springblade.manager.entity.ContractInfo;
 import org.springblade.manager.enums.StorageTypeEnum;
 import org.springblade.manager.feign.ContractClient;
@@ -25,6 +29,8 @@ import org.springframework.web.bind.annotation.RestController;
 import java.math.BigDecimal;
 import java.util.*;
 import java.util.function.Function;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
 import java.util.stream.Collectors;
 
 
@@ -352,4 +358,101 @@ public class ArchiveFileClientImpl implements ArchiveFileClient {
         return iArchiveFileService.getArchiveFileByArchivesId(archiveIds,null);
     }
 
+    @Override
+    public boolean findAndReplace(FindAndReplaceDto1 dto1) {
+        List<ArchiveFile> archiveFiles = dto1.getList();
+        FindAndReplaceDto dto = dto1.getDto();
+        List<ArchiveFile> updates = new ArrayList<>();
+
+        for (ArchiveFile archiveFile : archiveFiles) {
+            String originalName = archiveFile.getFileName();
+            if (StringUtils.isEmpty(originalName) || StringUtils.isEmpty(dto.getQuery())) {
+                continue;
+            }
+
+            if (!originalName.contains(dto.getQuery())) {
+                continue;
+            }
+
+            String newName = processFileName(originalName, dto);
+            if (!originalName.equals(newName)) {
+                ArchiveFile update = new ArchiveFile();
+                update.setId(archiveFile.getId());
+                update.setFileName(newName);
+                updates.add(update);
+            }
+        }
+
+        if (!updates.isEmpty()) {
+            return iArchiveFileService.updateBatchById(updates);
+        }
+        return true;
+    }
+
+    private String processFileName(String fileName, FindAndReplaceDto dto) {
+        String query = dto.getQuery();
+        String replace = dto.getReplace();
+
+        switch (dto.getType()) {
+            case 1: // 在指定位置插入
+                return handleInsertAtPosition(fileName, query, replace, dto.getPosition());
+
+            case 2: // 普通替换
+                return handleReplace(fileName, query, replace, false);
+
+            default: // 删除匹配内容
+                return handleReplace(fileName, query, "", true);
+        }
+    }
+
+    private String handleInsertAtPosition(String fileName, String query, String replace, Integer position) {
+        if (position == null) {
+            return fileName; // 没有指定位置时保持原样
+        }
+
+        StringBuilder sb = new StringBuilder();
+        int lastIndex = 0;
+        int index = fileName.indexOf(query);
+
+        while (index != -1) {
+            // 添加未处理部分
+            sb.append(fileName, lastIndex, index);
+
+            // 根据位置插入内容
+            switch (position) {
+                case 1: // 在查询内容前插入
+                    sb.append(replace).append(query);
+                    break;
+                case 2: // 在查询内容后插入
+                    sb.append(query).append(replace);
+                    break;
+                default:
+                    throw new ServiceException("请选择正确的定位条件");
+            }
+
+            lastIndex = index + query.length();
+            index = fileName.indexOf(query, lastIndex);
+        }
+
+        // 添加剩余部分
+        sb.append(fileName.substring(lastIndex));
+        return sb.toString();
+    }
+
+    private String handleReplace(String fileName, String query, String replacement, boolean isLiteral) {
+        if (isLiteral) {
+            // 字面量替换(避免正则表达式特殊字符问题)
+            return fileName.replace(query, replacement);
+        } else {
+            // 使用正则表达式替换,需要转义特殊字符
+            String escapedQuery = Pattern.quote(query); // 自动转义所有特殊字符
+            return fileName.replaceAll(escapedQuery, Matcher.quoteReplacement(replacement));
+        }
+    }
+
+    @Override
+    public List<ArchiveFile> getAllArchiveFileByIds(List<String> strList) {
+        return fileMapper.getAllArchiveFileByIds(strList);
+    }
+
 }

+ 118 - 0
blade-service/blade-business/src/main/java/org/springblade/business/feignClient/TrialCyAccessoriesClientImpl.java

@@ -0,0 +1,118 @@
+package org.springblade.business.feignClient;
+
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import lombok.AllArgsConstructor;
+import org.springblade.business.entity.TrialCyFinishTestReport;
+import org.springblade.business.entity.TrialCyThirdReport;
+import org.springblade.business.feign.TrialCyAccessoriesClient;
+import org.springblade.business.mapper.TrialSelfInspectionRecordMapper;
+import org.springblade.business.service.TrialCyFinishTestReportService;
+import org.springblade.business.service.TrialCyThirdReportService;
+import org.springblade.core.tool.utils.CollectionUtil;
+import org.springblade.manager.entity.TableFile;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * @author LHB
+ */
+@RestController
+@AllArgsConstructor
+public class TrialCyAccessoriesClientImpl implements TrialCyAccessoriesClient {
+
+    private final TrialSelfInspectionRecordMapper trialSelfInspectionRecordMapper;
+
+    /**
+     * 第三方、外委
+     */
+    private final TrialCyThirdReportService trialCyThirdReportService;
+
+    /**
+     * 试验报告
+     */
+    private final TrialCyFinishTestReportService trialCyFinishTestReportService;
+
+    @Override
+    public List<JSONObject> getTrialFilePdfRecord(String primaryKeyId, List<Integer> list) {
+        //获取id
+        List<Map<String, Object>> trialFilePdfRecord = trialSelfInspectionRecordMapper.getTrialFilePdfRecord(primaryKeyId, list);
+
+        if (CollectionUtil.isNotEmpty(trialFilePdfRecord)) {
+
+            //试验报告ids
+            List<Long> listOne = new ArrayList<>();
+            //第三方外委ids
+            List<Long> listTwo = new ArrayList<>();
+
+            for (Map<String, Object> stringObjectMap : trialFilePdfRecord) {
+
+                Integer type = (Integer) stringObjectMap.get("type");
+                Long recordId = (Long) stringObjectMap.get("record_id");
+                //试验报告
+                if (type == 11) {
+                    listOne.add(recordId);
+                } else {
+                    //第三方、外委
+                    listTwo.add(recordId);
+                }
+            }
+
+            List<JSONObject> result = new ArrayList<>();
+
+            if (CollectionUtil.isNotEmpty(listOne)) {
+                List<TrialCyFinishTestReport> list1 = trialCyFinishTestReportService.list(Wrappers.<TrialCyFinishTestReport>lambdaQuery()
+                        .isNotNull(TrialCyFinishTestReport::getAssembleFile)
+                        .in(TrialCyFinishTestReport::getTaskId, listOne)
+                );
+
+                if (CollectionUtil.isNotEmpty(list1)) {
+                    list1.forEach(f -> {
+                        String[] split = f.getAssembleFile().split("/");
+                        JSONObject jsonObject = new JSONObject();
+                        jsonObject.put("id", f.getTaskId());
+                        jsonObject.put("name", split[split.length - 1]);
+                        jsonObject.put("contractId", f.getContractId());
+                        jsonObject.put("domainUrl", f.getAssembleFile());
+                        jsonObject.put("domainPdfUrl", f.getAssembleFile());
+                        jsonObject.put("tabId", primaryKeyId);
+                        jsonObject.put("extension", "pdf");
+                        //是否为试验关联的附件
+                        jsonObject.put("isTrial", true);
+                        result.add(jsonObject);
+                    });
+                }
+            }
+            if (CollectionUtil.isNotEmpty(listTwo)) {
+                List<TrialCyThirdReport> list1 = trialCyThirdReportService.list(Wrappers.<TrialCyThirdReport>lambdaQuery()
+                        .isNotNull(TrialCyThirdReport::getAssembleFile)
+                        .in(TrialCyThirdReport::getId, listTwo)
+                );
+
+                if (CollectionUtil.isNotEmpty(list1)) {
+                    list1.forEach(f -> {
+                        String[] split = f.getAssembleFile().split("/");
+                        JSONObject jsonObject = new JSONObject();
+                        jsonObject.put("id", f.getId());
+                        jsonObject.put("name", split[split.length - 1]);
+                        jsonObject.put("contractId", f.getContractId());
+                        jsonObject.put("domainUrl", f.getAssembleFile());
+                        jsonObject.put("domainPdfUrl", f.getAssembleFile());
+                        jsonObject.put("tabId", primaryKeyId);
+                        jsonObject.put("extension", "pdf");
+                        //是否为试验关联的附件
+                        jsonObject.put("isTrial", true);
+                        result.add(jsonObject);
+                    });
+                }
+            }
+            return result;
+        }
+
+        return null;
+    }
+}

+ 15 - 5
blade-service/blade-business/src/main/java/org/springblade/business/feignClient/WbsTreeContractStatisticsClientImpl.java

@@ -9,6 +9,7 @@ import org.springblade.business.feign.WbsTreeContractStatisticsClient;
 import org.springblade.business.mapper.InformationQueryMapper;
 import org.springblade.business.service.IWbsTreeContractStatisticsService;
 import org.springblade.business.service.impl.WbsTreeContractStatisticsServiceImpl;
+import org.springblade.common.utils.SystemUtils;
 import org.springframework.data.redis.core.RedisTemplate;
 import org.springframework.data.redis.core.StringRedisTemplate;
 import org.springframework.jdbc.core.BeanPropertyRowMapper;
@@ -36,11 +37,14 @@ public class WbsTreeContractStatisticsClientImpl implements WbsTreeContractStati
 
     @Scheduled(cron = "0/30 * * * * ?")
     public void updateInformationQueryStatus() {
+        if (!SystemUtils.isLinux()) {
+            return;
+        }
         Map<String, String> map = new HashMap<>();
-        List<String> queryIds = redisTemplate.opsForList().range(INFORMATION_QUERY_STATUS_STATISTICS_KEY, 0, 100);
+        List<String> queryIds = redisTemplate.opsForList().range(INFORMATION_QUERY_STATUS_STATISTICS_KEY, 0, 1000);
         if (queryIds != null && !queryIds.isEmpty()) {
             String ids = queryIds.stream().distinct().collect(Collectors.joining(","));
-            List<InformationQuery> queryList = jdbcTemplate.query("select wbs_id, classify, contract_id from u_information_query where id in ( " + ids +" ) and is_deleted = 0 group by contract_id,wbs_id,classify",
+            List<InformationQuery> queryList = jdbcTemplate.query("select id,wbs_id, classify, contract_id from u_information_query where id in ( " + ids +" ) and is_deleted = 0 group by contract_id,wbs_id,classify",
                     new BeanPropertyRowMapper<>(InformationQuery.class));
             if (!queryList.isEmpty()) {
                 for (InformationQuery query : queryList) {
@@ -55,9 +59,9 @@ public class WbsTreeContractStatisticsClientImpl implements WbsTreeContractStati
                         log.error("updateInformationQueryStatus wbsId = {}, contractId = {}, classify = {}", query.getWbsId(), query.getContractId(), query.getClassify() , e);
                     }
                 }
-                for (String queryId : queryIds) {
-                    redisTemplate.opsForList().remove("blade:statistics:information_query_statistics_key", 1, queryId);
-                }
+            }
+            for (String queryId : queryIds) {
+                redisTemplate.opsForList().remove("blade:statistics:information_query_statistics_key", 1, queryId);
             }
         }
     }
@@ -160,4 +164,10 @@ public class WbsTreeContractStatisticsClientImpl implements WbsTreeContractStati
     public void statisticsContract(Long contractId) {
         wbsTreeContractStatisticsService.statisticsContract(contractId);
     }
+
+    @Override
+    @Async
+    public void updateAncestors(String ids) {
+        wbsTreeContractStatisticsService.updateAncestors(ids);
+    }
 }

+ 2 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/ArchiveFileMapper.java

@@ -120,4 +120,6 @@ public interface ArchiveFileMapper extends BaseMapper<ArchiveFile> {
      * @return
      */
     Map<String, BigDecimal> getAllArchiveAutoByContractTypeSummary(@Param("projectId") Long projectId);
+
+    List<ArchiveFile> getAllArchiveFileByIds(@Param("strList") List<String> strList);
 }

+ 9 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/ArchiveFileMapper.xml

@@ -554,4 +554,13 @@
       ) a
 
     </select>
+    <select id="getAllArchiveFileByIds" resultType="org.springblade.business.entity.ArchiveFile">
+        select * from u_archive_file where is_deleted = 0
+        <if test="strList != null and strList != ''">
+            and id in
+            <foreach collection="strList" item="id" open="(" separator="," close=")">
+                #{id}
+            </foreach>
+        </if>
+    </select>
 </mapper>

+ 18 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/ContractLogMonthPackMapper.java

@@ -0,0 +1,18 @@
+package org.springblade.business.mapper;
+
+import org.springblade.business.entity.ContractLogMonthPack;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+
+/**
+* @author LHB
+* @description 针对表【u_contract_log_month_pack(日志按月封装表)】的数据库操作Mapper
+* @createDate 2025-08-20 14:35:00
+* @Entity generator.domain.UContractLogMonthPack
+*/
+public interface ContractLogMonthPackMapper extends BaseMapper<ContractLogMonthPack> {
+
+}
+
+
+
+

+ 28 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/ContractLogMonthPackMapper.xml

@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper
+        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.ContractLogMonthPackMapper">
+
+    <resultMap id="BaseResultMap" type="org.springblade.business.entity.ContractLogMonthPack">
+            <id property="id" column="id" />
+            <result property="projectId" column="project_id" />
+            <result property="contractId" column="contract_id" />
+            <result property="wbsNodeId" column="wbs_node_id" />
+            <result property="wbsNodeType" column="wbs_node_type" />
+            <result property="fileName" column="file_name" />
+            <result property="recordTime" column="record_time" />
+            <result property="contractName" column="contract_name" />
+            <result property="page" column="page" />
+            <result property="createTime" column="create_time" />
+            <result property="createUser" column="create_user" />
+            <result property="updateTime" column="update_time" />
+            <result property="updateUser" column="update_user" />
+    </resultMap>
+
+    <sql id="Base_Column_List">
+        id,project_id,contract_id,wbs_node_id,wbs_node_type,file_name,
+        record_time,contract_name,page,create_time,create_user,
+        update_time,update_user
+    </sql>
+</mapper>

+ 3 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/EntrustInfoMapper.xml

@@ -71,6 +71,9 @@
         <if test="param2.entrustName != null and param2.entrustName != ''">
             AND ( a.entrust_name like CONCAT(CONCAT('%', #{param2.entrustName}), '%') or a.entrust_no like CONCAT(CONCAT('%', #{param2.entrustName}), '%') or b.material_name like CONCAT(CONCAT('%', #{param2.entrustName}), '%'))
         </if>
+        <if test="param2.entrustNo != null and param2.entrustNo != ''">
+            AND a.entrust_no like CONCAT(CONCAT('%', #{param2.entrustNo}), '%')
+        </if>
     </select>
 
     <select id="getReportDetail" resultType="org.springblade.business.vo.EntrustDataInfoVO">

+ 1 - 1
blade-service/blade-business/src/main/java/org/springblade/business/mapper/ImageClassificationFileMapper.xml

@@ -126,7 +126,7 @@
                 order by shooting_time desc
             ) as files
         where
-            1 = 1
+        1 = 1
         <if test="param.queryDate != null and param.queryDate != ''">
             and files.shootingTimeStr like concat('%',#{param.queryDate},'%')
         </if>

+ 9 - 2
blade-service/blade-business/src/main/java/org/springblade/business/mapper/InformationQueryMapper.java

@@ -17,6 +17,7 @@
 package org.springblade.business.mapper;
 
 import org.springblade.business.entity.InformationQuery;
+import org.springblade.business.vo.ChekPdfPaceVo;
 import org.springblade.business.vo.InformationQueryVO;
 import com.baomidou.mybatisplus.core.mapper.BaseMapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
@@ -42,7 +43,7 @@ public interface InformationQueryMapper extends BaseMapper<InformationQuery> {
 
     List<WbsTreeContractTreeVOS> queryContractTree(@Param("contractId") String contractId, @Param("parentId") String parentId, @Param("classify") Integer classify);
 
-    List<QueryProcessDataVO> queryProcessDataByPrimaryKeyIdAndClassify(@Param("primaryKeyId") String primaryKeyId, @Param("classify") Integer classify);
+    List<QueryProcessDataVO> queryProcessDataByPrimaryKeyIdAndClassify(@Param("primaryKeyId") String primaryKeyId, @Param("classify") Integer classify, @Param("dateIsComplete") Integer dateIsComplete);
 
     /**
      * 查询工序节点的填报记录
@@ -57,7 +58,7 @@ public interface InformationQueryMapper extends BaseMapper<InformationQuery> {
     /**
      * 查询工序节点的填报记录
      */
-    List<QueryProcessDataVO> queryProcessDataByParentIdAndContractIdTwo(@Param("parentId") String parentId, @Param("classify") Integer classify, @Param("contractId") String contractId);
+    List<QueryProcessDataVO> queryProcessDataByParentIdAndContractIdTwo(@Param("parentId") String parentId, @Param("classify") Integer classify, @Param("contractId") String contractId, @Param("dateIsComplete") Integer dateIsComplete);
 
     /**
      * 查询工序节点的填报记录3
@@ -145,4 +146,10 @@ public interface InformationQueryMapper extends BaseMapper<InformationQuery> {
     List<TabBusstimeInfo> getTabussTimeInfo(@Param("tables") List<String> tables);
 
     List<Long> getInfoByNodeIds(@Param("ids") List<Long> ids);
+
+    int addCheckPdfInfoByNodeId(@Param("ids") String ids,@Param("classify") String classify);
+
+    int addCheckPdfInfoByIds(@Param("ids") List<String> ids,@Param("classify") String classify);
+
+    ChekPdfPaceVo getCheckPdfPaceInfo(@Param("contractId") String contractI, @Param("classify") String classify);
 }

+ 54 - 22
blade-service/blade-business/src/main/java/org/springblade/business/mapper/InformationQueryMapper.xml

@@ -50,6 +50,13 @@
         <result column="evaluate" property="evaluate"/>
         <result column="queryType" property="queryType"/>
         <result column="isExperiment" property="isExperiment"/>
+        <result column="dateIsComplete" property="dateIsComplete"/>
+        <result column="infoQueryName" property="infoQueryName"/>
+        <result column="pdfUrl" property="pdfUrl"/>
+        <result column="privateTableFileType" property="privateTableFileType"/>
+        <result column="contractTableFileType" property="contractTableFileType"/>
+        <result column="contractTableFileTypeTwo" property="contractTableFileTypeTwo"/>
+        <result column="pdfUrl" property="pdfUrl"/>
     </resultMap>
 
     <resultMap id="queryContractTreeMap" type="org.springblade.manager.vo.WbsTreeContractTreeVOS">
@@ -428,10 +435,16 @@
                wtc.p_key_id,
                wtc.ancestors,
                wtc.major_data_type,
+               case when wtc.date_is_complete = 1 then '是' else '否' end AS dateIsComplete,
                IFNULL(if(length(trim(wtc.full_name)) > 0, wtc.full_name, wtc.node_name), wtc.node_name) AS     title,
                wtc.parent_id                                                                            AS     parentId,
                uiq.id                                                                                   AS     informationQueryId,
+               uiq.name                                                                                   AS     infoQueryName,
+               uiq.pdf_url                                                                                   AS     pdfUrl,
                uiq.status,
+               p.table_file_type									                                    AS privateTableFileType,
+               (select GROUP_CONCAT(DISTINCT table_file_type) from u_trial_file_pdf_record where node_id = wtc.p_key_id) contractTableFileType,
+               (select GROUP_CONCAT(DISTINCT type) from m_table_file where tab_id = wtc.p_key_id and is_deleted = 0 and classify = #{classify}) contractTableFileTypeTwo,
                (
                    select case iq.status
                               WHEN 2 then 'true'
@@ -450,26 +463,14 @@
         AS isExperiment
         FROM
         m_wbs_tree_contract AS wtc
-        LEFT JOIN u_information_query AS uiq ON wtc.p_key_id = uiq.wbs_id AND uiq.classify =
-        #{classify}
-        and
-        uiq
-        .
-        is_deleted
-        =
-        0
+        LEFT JOIN u_information_query AS uiq ON wtc.p_key_id = uiq.wbs_id AND uiq.classify = #{classify} and uiq.is_deleted =  0 and uiq.status != 3
+        left join m_wbs_tree_private p on wtc.is_type_private_pid = p.p_key_id
         WHERE
-        wtc
-        .
-        p_key_id
-        =
-        #{primaryKeyId}
-        AND
-        wtc
-        .
-        is_deleted
-        =
-        0
+        wtc.p_key_id = #{primaryKeyId}
+        AND  wtc.is_deleted = 0
+        <if test="dateIsComplete != null">
+            AND wtc.date_is_complete = #{dateIsComplete}
+        </if>
     </select>
 
     <select id="queryProcessDataByParentIdAndContractId" resultMap="queryProcessDataMap">
@@ -822,6 +823,7 @@
     </select>
     <select id="queryProcessDataByParentIdAndContractIdTwo" resultMap="queryProcessDataMap">
         SELECT wtc.id                                                                                   AS treeId,
+               case when wtc.date_is_complete = 1 then '是' else '否' end                                AS dateIsComplete,
                wtc.p_key_id,
                wtc.ancestors,
                wtc.major_data_type,
@@ -831,20 +833,28 @@
                uiq.id                                                                                   AS informationQueryId,
                IFNULL(uiq.status, 0)                                                                    AS status,
                uiq.type                                                                                 AS queryType,
+               uiq.name                                                                                 AS infoQueryName,
+               uiq.pdf_url                                                                              AS pdfUrl,
+               p.table_file_type									                                    AS privateTableFileType,
+               (select GROUP_CONCAT(DISTINCT table_file_type) from u_trial_file_pdf_record where node_id = wtc.p_key_id) contractTableFileType,
+               (select GROUP_CONCAT(DISTINCT type) from m_table_file where tab_id = wtc.p_key_id and is_deleted = 0 and classify = #{classify}) contractTableFileTypeTwo,
                case
                    WHEN uiq.pdf_trial_url is null then 'false'
                    ELSE 'true' end                                                                      AS isExperiment
         FROM m_wbs_tree_contract AS wtc
                  LEFT JOIN u_information_query AS uiq
                            ON wtc.p_key_id = uiq.wbs_id AND uiq.classify = #{classify} and uiq.is_deleted = 0 and
-                              wtc.is_deleted = 0 and
-                              wtc.status = 1
+                              uiq.status != 3
+                 left join m_wbs_tree_private p on wtc.is_type_private_pid = p.p_key_id
         WHERE wtc.type = 1
           AND wtc.major_data_type in (0, 1, 2, 3, 4)
-          AND wtc.ancestors like concat('%', #{parentId}, '%')
+          AND wtc.ancestors_p_id like concat(#{parentId}, '%')
           AND wtc.contract_id = #{contractId}
           AND wtc.is_deleted = 0
           AND wtc.status = 1
+        <if test="dateIsComplete != null">
+            AND wtc.date_is_complete = #{dateIsComplete}
+        </if>
     </select>
 
     <select id="queryProcessDataByParentIdAndContractId_3" resultMap="queryProcessDataMap">
@@ -998,4 +1008,26 @@
             #{id}
         </foreach>
     </select>
+
+    <update id="addCheckPdfInfoByNodeId" >
+        update u_information_query a set a.chek_status=1
+        where a.is_deleted = 0 and a.classify=#{classify} and a.wbs_id
+        in( select b.p_key_id from m_wbs_tree_contract b where b.is_deleted = 0 and b.ancestors_p_id like CONCAT(CONCAT('%', #{ids}), '%') and b.is_deleted = 0) and a.status in(1,2)
+    </update>
+
+    <update id="addCheckPdfInfoByIds">
+        update u_information_query set chek_status=1
+        where is_deleted = 0 and classify=#{classify} and id in
+        <foreach collection="ids" item="id" open="(" separator="," close=")">
+            #{id}
+        </foreach>
+    </update>
+
+
+    <select id="getCheckPdfPaceInfo" resultType="org.springblade.business.vo.ChekPdfPaceVo">
+        SELECT c.TotalCount,c.finishCount, IF(FLOOR(finishCount/TotalCount),null,0) as pace from (
+           SELECT COUNT(1) as TotalCount,IF(SUM(IF(status = 'chek_status', 1, 0)),null,0) AS finishCount from u_information_query where contract_id=#{contractId} and classify=#{classify} and chek_status in(1,2,3)
+        ) c
+    </select>
+
 </mapper>

+ 17 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/RecycleBinInfoMapper.java

@@ -0,0 +1,17 @@
+package org.springblade.business.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import org.apache.ibatis.annotations.Param;
+import org.springblade.business.entity.RecycleBinInfo;
+import org.springblade.business.vo.RecycleBinInfoVO;
+
+import java.util.Collection;
+
+public interface RecycleBinInfoMapper extends BaseMapper<RecycleBinInfo> {
+
+
+    IPage<RecycleBinInfo> page(IPage<RecycleBinInfo> iPage, @Param("vo") RecycleBinInfoVO recycleBinInfoVO);
+
+    Collection<RecycleBinInfo> queryOperation(Collection<Long> ids);
+}

+ 95 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/RecycleBinInfoMapper.xml

@@ -0,0 +1,95 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.RecycleBinInfoMapper">
+
+    <!-- 通用查询映射结果 -->
+    <resultMap id="recycleBinResultMap" type="org.springblade.business.entity.RecycleBinInfo">
+        <result column="id" property="id"/>
+        <result column="create_user" property="createUser"/>
+        <result column="create_dept" property="createDept"/>
+        <result column="create_time" property="createTime"/>
+        <result column="update_user" property="updateUser"/>
+        <result column="update_time" property="updateTime"/>
+        <result column="status" property="status"/>
+        <result column="is_deleted" property="isDeleted"/>
+        <result column="project_id" property="projectId"/>
+        <result column="contract_id" property="contractId"/>
+        <result column="del_type" property="delType"/>
+        <result column="file_name" property="fileName"/>
+        <result column="position" property="position"/>
+        <result column="business_id" property="businessId"/>
+        <result column="operation_time" property="operationTime"/>
+        <result column="create_user_name" property="createUserName"/>
+        <result column="update_user_name" property="updateUserName"/>
+        <result column="del_id" property="delId"/>
+        <result column="del_root_id" property="delRootId"/>
+        <result column="del_root_name" property="delRootName"/>
+        <result column="operation_id" property="operationId"/>
+        <result column="jl_file_name" property="jlFileName"/>
+        <result column="is_data" property="isData"/>
+    </resultMap>
+
+    <sql id="includeSql" >
+        id, create_user, create_dept, create_time, update_user, update_time, status, is_deleted, project_id, contract_id, del_type, file_name, position, business_id, operation_time, create_user_name, update_user_name, del_id, del_root_id, del_root_name, operation_id, jl_file_name, is_data
+    </sql>
+    <select id="page" resultMap="recycleBinResultMap">
+        select
+        <include refid="includeSql"/>
+        from u_recycle_bin_info
+        where is_deleted = 0
+        <if test="vo.contractId != null">
+            and contract_id = #{vo.contractId}
+        </if>
+        <if test="vo.delType != null">
+            and del_type = #{vo.delType}
+        </if>
+        <if test="vo.isData != null">
+            and is_data = #{vo.isData}
+        </if>
+        <if test="vo.recycleType != null">
+            and status = #{vo.recycleType}
+            <if test="vo.recycleType == 1">
+                <if test="vo.startTime != null">
+                    and create_time >= #{vo.startTime}
+                </if>
+                <if test="vo.endTime != null">
+                    and create_time &lt;= #{vo.endTime}
+                </if>
+                <if test="vo.userId != null">
+                    and create_user = #{vo.userId}
+                </if>
+            </if>
+            <if test="vo.recycleType == 0">
+                <if test="vo.startTime != null">
+                    and update_time >= #{vo.startTime}
+                </if>
+                <if test="vo.endTime != null">
+                    and update_time &lt;= #{vo.endTime}
+                </if>
+                <if test="vo.userId != null">
+                    and update_user = #{vo.userId}
+                </if>
+            </if>
+        </if>
+        <if test="vo.content != null and vo.content != ''">
+            and (file_name like concat('%',#{vo.content},'%') or jl_file_name like concat('%',#{vo.content},'%') or del_root_name like concat('%',#{vo.content},'%') or position like concat('%',#{vo.content},'%'))
+        </if>
+        <if test="vo.operationId != null">
+            and operation_id = #{vo.operationId}
+        </if>
+        order by
+        <if test="vo.recycleType == 1">
+            create_time desc
+        </if>
+        <if test="vo.recycleType == 0">
+            update_time desc
+        </if>
+    </select>
+    <select id="queryOperation" resultType="org.springblade.business.entity.RecycleBinInfo">
+        select del_root_id,del_root_name from u_recycle_bin_info where del_root_id in ( select del_root_id from u_recycle_bin_info where id in (
+            <foreach collection="ids" item="id" separator=",">
+                #{id}
+            </foreach>
+            ) and is_deleted = 0 group by del_root_id ) and status = 0  group by del_root_id, del_root_name having count(1) > 1
+    </select>
+</mapper>

+ 50 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialClassificationTreeMapper.java

@@ -0,0 +1,50 @@
+/*
+ *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ *
+ *  Redistributions of source code must retain the above copyright notice,
+ *  this list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright
+ *  notice, this list of conditions and the following disclaimer in the
+ *  documentation and/or other materials provided with the distribution.
+ *  Neither the name of the dreamlu.net developer nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ *  Author: Chill 庄骞 (smallchill@163.com)
+ */
+package org.springblade.business.mapper;
+
+import org.apache.ibatis.annotations.Param;
+import org.springblade.business.entity.TrialClassificationTree;
+import org.springblade.business.vo.TrialClassificationTreeVO;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import java.util.List;
+
+/**
+ * 德飞试验系统检测分类树 Mapper 接口
+ *
+ * @author BladeX
+ * @since 2025-08-15
+ */
+public interface TrialClassificationTreeMapper extends BaseMapper<TrialClassificationTree> {
+
+	/**
+	 * 自定义分页
+	 *
+	 * @param page
+	 * @param trialClassificationTree
+	 * @return
+	 */
+	List<TrialClassificationTreeVO> selectTrialClassificationTreePage(IPage page, TrialClassificationTreeVO trialClassificationTree);
+
+    void deleteById1(Long id);
+
+	Long selectAncestors(Long parentId);
+
+    List<TrialClassificationTreeVO> selectAllNode(@Param("id") Long id, @Param("projectId") Long projectId);
+
+	void deleteByGroupType(@Param("groupType") Integer groupType);
+}

+ 45 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialClassificationTreeMapper.xml

@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.TrialClassificationTreeMapper">
+
+    <!-- 通用查询映射结果 -->
+    <resultMap id="trialClassificationTreeResultMap" type="org.springblade.business.entity.TrialClassificationTree">
+        <result column="id" property="id"/>
+        <result column="is_deleted" property="isDeleted"/>
+        <result column="parent_id" property="parentId"/>
+        <result column="classification_name" property="classificationName"/>
+    </resultMap>
+    <update id="deleteById1">
+        update u_trial_classification_tree set is_deleted = 1 where classification_ancestors  like concat('%',#{id},'%')
+    </update>
+    <delete id="deleteByGroupType">
+        delete from u_trial_classification_tree where group_type = #{groupType}
+    </delete>
+
+
+    <select id="selectTrialClassificationTreePage" resultMap="trialClassificationTreeResultMap">
+        select * from u_trial_classification_tree where is_deleted = 0
+    </select>
+    <select id="selectAncestors" resultType="java.lang.Long">
+        select parent_id from u_trial_classification_tree where id = #{parentId} and is_deleted = 0
+    </select>
+    <select id="selectAllNode" resultType="org.springblade.business.vo.TrialClassificationTreeVO">
+        select tree.id,tree.parent_id,tree.project_id,tree.classification_name,(
+            SELECT
+                CASE WHEN count(1) > 0 THEN 1 ELSE 0 END
+            FROM
+             u_trial_classification_tree
+            WHERE
+                parent_id = tree.id and is_deleted = 0
+        ) AS "has_children"
+        from u_trial_classification_tree tree
+        where tree.is_deleted = 0 and tree.project_id = #{projectId}
+        <if test="id!=null and id!=''">
+            and tree.parent_id = #{id}
+        </if>
+        <if test="id==null or id==''">
+            and tree.parent_id = 0
+        </if>
+    </select>
+
+</mapper>

+ 27 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyAccessoriesMapper.java

@@ -0,0 +1,27 @@
+package org.springblade.business.mapper;
+
+import org.apache.ibatis.annotations.Param;
+import org.springblade.business.entity.TrialCyAccessories;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+
+import java.util.List;
+import java.util.Objects;
+
+/**
+* @author LHB
+* @description 针对表【u_trial_cy_accessories(成渝-附件信息)】的数据库操作Mapper
+* @createDate 2025-08-04 14:39:16
+* @Entity generator.domain.UTrialCyAccessories
+*/
+public interface TrialCyAccessoriesMapper extends BaseMapper<TrialCyAccessories> {
+
+    Boolean clearTrialAssociation(@Param("nodeId") Long nodeId,
+                                  @Param("recordId") Long recordId);
+
+    List<String> selectFilePdfList(@Param("nodeId") Long nodeId,
+                                   @Param("types") Integer... types);
+}
+
+
+
+

+ 28 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyAccessoriesMapper.xml

@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper
+        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.TrialCyAccessoriesMapper">
+
+    <resultMap id="BaseResultMap" type="org.springblade.business.entity.TrialCyAccessories">
+            <id property="id" column="id" />
+            <result property="reportId" column="report_id" />
+            <result property="accId" column="acc_id" />
+            <result property="accType" column="acc_type" />
+            <result property="fileName" column="file_name" />
+            <result property="filePath" column="file_path" />
+    </resultMap>
+
+    <sql id="Base_Column_List">
+        id,report_id,acc_id,acc_type,file_name,file_path
+    </sql>
+    <delete id="clearTrialAssociation">
+        delete from u_trial_file_pdf_record where node_id = #{nodeId} and record_id=#{recordId}
+    </delete>
+    <select id="selectFilePdfList" resultType="java.lang.String">
+        select record_id from u_trial_file_pdf_record where node_id = #{nodeId} and type in
+          <foreach collection="types" item="type" open="(" close=")" separator=",">
+              #{type}
+          </foreach>
+    </select>
+</mapper>

+ 23 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyFinishTestReportMapper.java

@@ -0,0 +1,23 @@
+package org.springblade.business.mapper;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.apache.ibatis.annotations.Param;
+import org.springblade.business.entity.TrialCyFinishTestReport;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import org.springblade.business.vo.ThirdReportVo;
+import org.springblade.business.vo.TrialCyThirdReportQueryVo;
+
+/**
+* @author LHB
+* @description 针对表【u_trial_cy_finish_test_report(成渝-获取标段已完成(已签章完成)的检测报告)】的数据库操作Mapper
+* @createDate 2025-08-01 09:05:03
+* @Entity generator.domain.UTrialCyFinishTestReport
+*/
+public interface TrialCyFinishTestReportMapper extends BaseMapper<TrialCyFinishTestReport> {
+
+    Page<ThirdReportVo> myPage(Page<ThirdReportVo> page, @Param("query") TrialCyThirdReportQueryVo queryVo);
+}
+
+
+
+

+ 37 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyFinishTestReportMapper.xml

@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper
+        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.TrialCyFinishTestReportMapper">
+    <select id="myPage" resultType="org.springblade.business.vo.ThirdReportVo">
+        select
+            task_id id,
+            contract_id contractId,
+            report_number reportNo,
+            report_date reportDate,
+            position projectPositionName,
+            case
+                when experiment_result = 1 then '合格'
+                else '不合格'
+            end detectionResultName,
+        (select count(0) > 0 from u_trial_file_pdf_record where node_id = #{query.qualityTestPKeyId}  and type = 11 and record_id = t.id) isSelectedStatus
+        from u_trial_cy_finish_test_report t
+        <where>
+            <if test="query.contractId != null">
+                AND contract_id = #{query.contractId}
+            </if>
+            <if test="query.nodeId != null">
+                AND exam_name_info_id = #{query.nodeId}
+            </if>
+            <if test="query.startTime != null">
+                AND report_date >= #{query.startTime}
+            </if>
+            <if test="query.endTime != null">
+                AND report_date &lt;= #{query.endTime}
+            </if>
+            <if test="query.reportType != null">
+                AND cs = #{query.reportType}
+            </if>
+        </where>
+    </select>
+</mapper>

+ 23 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyTestTypeMapper.java

@@ -0,0 +1,23 @@
+package org.springblade.business.mapper;
+
+import org.apache.ibatis.annotations.Param;
+import org.springblade.business.entity.TrialCyTestType;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+
+import java.util.List;
+
+/**
+* @author LHB
+* @description 针对表【u_trial_cy_test_type(成渝-试验检测树)】的数据库操作Mapper
+* @createDate 2025-08-01 09:05:07
+* @Entity generator.domain.UTrialCyTestType
+*/
+public interface TrialCyTestTypeMapper extends BaseMapper<TrialCyTestType> {
+
+    List<TrialCyTestType> getTree(@Param("projectId") Long projectId,
+                                  @Param("parentId") String parentId);
+}
+
+
+
+

+ 24 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyTestTypeMapper.xml

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper
+        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.TrialCyTestTypeMapper">
+    <sql id="Base_sql">
+        p_key_id,
+        project_id,
+        id,
+        father_id,
+        name,
+        order_index,
+        create_time
+    </sql>
+    <select id="getTree" resultType="org.springblade.business.entity.TrialCyTestType">
+        select
+            <include refid="Base_sql"/>,
+            (select count(1) > 0 from u_trial_cy_test_type where father_id = t.id) has_children
+        from u_trial_cy_test_type t
+        where project_id = #{projectId}
+          and father_id = #{parentId}
+        order by order_index
+    </select>
+</mapper>

+ 24 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyThirdReportMapper.java

@@ -0,0 +1,24 @@
+package org.springblade.business.mapper;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import org.apache.ibatis.annotations.Param;
+import org.springblade.business.entity.TrialCyThirdReport;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import org.springblade.business.vo.ThirdReportVo;
+import org.springblade.business.vo.TrialCyThirdReportQueryVo;
+
+/**
+* @author LHB
+* @description 针对表【u_trial_cy_third_report(成渝-已上传的外委检测报告/第三方检测报告/上传报告)】的数据库操作Mapper
+* @createDate 2025-08-01 09:05:10
+* @Entity generator.domain.UTrialCyThirdReport
+*/
+public interface TrialCyThirdReportMapper extends BaseMapper<TrialCyThirdReport> {
+
+    Page<ThirdReportVo> myPage(Page<ThirdReportVo> page,
+                               @Param("query") TrialCyThirdReportQueryVo queryVo);
+}
+
+
+
+

+ 36 - 0
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialCyThirdReportMapper.xml

@@ -0,0 +1,36 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper
+        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
+        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="org.springblade.business.mapper.TrialCyThirdReportMapper">
+    <select id="myPage" resultType="org.springblade.business.vo.ThirdReportVo">
+        select
+            id,
+            contract_id contractId,
+            report_no reportNo,
+            report_date reportDate,
+            project_part projectPositionName,
+            case when is_qualified = 1 then '合格'
+                else '不合格'
+            end detectionResultName,
+        (select count(0) > 0 from u_trial_file_pdf_record where node_id = #{query.qualityTestPKeyId}  and type in(12,13) and record_id = t.id) isSelectedStatus
+        from u_trial_cy_third_report t
+        <where>
+            <if test="query.contractId != null">
+                AND contract_id = #{query.contractId}
+            </if>
+            <if test="query.type != null">
+                AND `third_type` = #{query.type}
+            </if>
+            <if test="query.startTime != null">
+                AND report_date >= #{query.startTime}
+            </if>
+            <if test="query.endTime != null">
+                AND report_date &lt;= #{query.endTime}
+            </if>
+            <if test="query.nodeId != null">
+                AND exam_name_info_id = #{query.nodeId}
+            </if>
+        </where>
+    </select>
+</mapper>

+ 4 - 1
blade-service/blade-business/src/main/java/org/springblade/business/mapper/TrialSelfInspectionRecordMapper.java

@@ -7,6 +7,7 @@ import org.springblade.business.entity.TrialSelfInspectionRecord;
 import org.springblade.manager.entity.WbsTreeContract;
 
 import java.util.List;
+import java.util.Map;
 
 public interface TrialSelfInspectionRecordMapper extends BaseMapper<TrialSelfInspectionRecord> {
 
@@ -34,7 +35,7 @@ public interface TrialSelfInspectionRecordMapper extends BaseMapper<TrialSelfIns
 
     void deleteSeletedStatusByNodeId(String nodeId, Integer type, String recordId);
 
-    void insertSeletedStatus(Long id, String nodeId, Integer type, String recordId);
+    void insertSeletedStatus(Long id, String nodeId, Integer type, String recordId, String tableFileType);
 
     List<String> selectCountSeletedStatus(String nodeId, Integer type);
 
@@ -45,4 +46,6 @@ public interface TrialSelfInspectionRecordMapper extends BaseMapper<TrialSelfIns
     @Select("select self_id from u_trial_self_quality_project where quality_node_id = #{pKeyId}")
     List<String> selectTrialIdByNodeId(Long pKeyId);
 
+    List<Map<String,Object>> getTrialFilePdfRecord(@Param("nodeId") String nodeId,
+                                                   @Param("types") List<Integer> types);
 }

이 변경점에서 너무 많은 파일들이 변경되어 몇몇 파일들은 표시되지 않았습니다.