From 92eb695ac1254708feb6e740432fc5da9e1ad42b Mon Sep 17 00:00:00 2001
From: 云 <2163098428@qq.com>
Date: 星期三, 08 七月 2026 15:37:12 +0800
Subject: [PATCH] Merge branch 'dev_New_pro' into dev_山西_黎城康森商砼
---
src/main/java/com/ruoyi/approve/service/impl/ApprovalTemplateServiceImpl.java | 308 +++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 308 insertions(+), 0 deletions(-)
diff --git a/src/main/java/com/ruoyi/approve/service/impl/ApprovalTemplateServiceImpl.java b/src/main/java/com/ruoyi/approve/service/impl/ApprovalTemplateServiceImpl.java
new file mode 100644
index 0000000..9a5f0b8
--- /dev/null
+++ b/src/main/java/com/ruoyi/approve/service/impl/ApprovalTemplateServiceImpl.java
@@ -0,0 +1,308 @@
+package com.ruoyi.approve.service.impl;
+
+import cn.hutool.core.collection.CollUtil;
+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.Wrappers;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.ruoyi.approve.bean.dto.ApprovalTemplateDto;
+import com.ruoyi.approve.bean.vo.ApprovalTemplateNodeApproverVo;
+import com.ruoyi.approve.bean.vo.ApprovalTemplateNodeVo;
+import com.ruoyi.approve.bean.vo.ApprovalTemplateVo;
+import com.ruoyi.approve.mapper.ApprovalTemplateMapper;
+import com.ruoyi.approve.mapper.ApprovalTemplateNodeApproverMapper;
+import com.ruoyi.approve.mapper.ApprovalInstanceMapper;
+import com.ruoyi.approve.pojo.ApprovalInstance;
+import com.ruoyi.approve.pojo.ApprovalTemplate;
+import com.ruoyi.approve.pojo.ApprovalTemplateNode;
+import com.ruoyi.approve.pojo.ApprovalTemplateNodeApprover;
+import com.ruoyi.approve.service.ApprovalTemplateNodeService;
+import com.ruoyi.approve.service.ApprovalTemplateService;
+import com.ruoyi.basic.dto.StorageBlobDTO;
+import com.ruoyi.basic.enums.ApplicationTypeEnum;
+import com.ruoyi.basic.enums.RecordTypeEnum;
+import com.ruoyi.basic.utils.FileUtil;
+import lombok.RequiredArgsConstructor;
+import org.springframework.beans.BeanUtils;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.util.CollectionUtils;
+
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+/**
+ * <p>
+ * 瀹℃壒妯℃澘鏈嶅姟瀹炵幇绫�
+ * </p>
+ *
+ * @since 2026-05-18 11:20:08
+ */
+@Service
+@RequiredArgsConstructor
+public class ApprovalTemplateServiceImpl extends ServiceImpl<ApprovalTemplateMapper, ApprovalTemplate> implements ApprovalTemplateService {
+
+ private final ApprovalTemplateMapper approvalTemplateMapper;
+ private final ApprovalTemplateNodeService approvalTemplateNodeService;
+ private final ApprovalTemplateNodeApproverMapper approvalTemplateNodeApproverMapper;
+ private final ApprovalInstanceMapper approvalInstanceMapper;
+ private final FileUtil fileUtil;
+
+ @Override
+ public IPage<ApprovalTemplateVo> listPage(Page<ApprovalTemplateVo> page, ApprovalTemplateDto approvalTemplateDto) {
+ IPage<ApprovalTemplateVo> approvalTemplateVoIPage = approvalTemplateMapper.listPage(page, approvalTemplateDto);
+ fillTemplateVoNodes(approvalTemplateVoIPage.getRecords());
+ return approvalTemplateVoIPage;
+ }
+
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public Boolean saveApprovalTemplateDto(ApprovalTemplateDto approvalTemplateDto) {
+ approvalTemplateMapper.insert(approvalTemplateDto);
+ approvalTemplateNodeService.remove(
+ new LambdaQueryWrapper<ApprovalTemplateNode>()
+ .eq(ApprovalTemplateNode::getTemplateId, approvalTemplateDto.getId())
+ );
+ approvalTemplateNodeApproverMapper.delete(
+ new LambdaQueryWrapper<ApprovalTemplateNodeApprover>()
+ .eq(ApprovalTemplateNodeApprover::getTemplateId, approvalTemplateDto.getId())
+ );
+ // 淇濆瓨闄勪欢
+ List<StorageBlobDTO> storageBlobDTOs = approvalTemplateDto.getStorageBlobDTOs();
+ if (!CollectionUtils.isEmpty(storageBlobDTOs)) {
+ fileUtil.saveStorageAttachment(ApplicationTypeEnum.FILE, RecordTypeEnum.APPROVAL_TEMPLATE, approvalTemplateDto.getId(), storageBlobDTOs);
+ }
+ return approvalTemplateNodeService.saveApprovalTemplateNode(
+ approvalTemplateDto.getId(),
+ approvalTemplateDto.getNodes()
+ );
+ }
+
+ @Override
+ public Boolean updateApprovalTemplateDto(ApprovalTemplateDto approvalTemplateDto) {
+ // 妫�鏌ユā鏉挎槸鍚﹁瀹℃壒瀹炰緥寮曠敤
+ if (isTemplateReferenced(approvalTemplateDto.getId())) {
+ throw new RuntimeException("璇ュ鎵规ā鏉垮凡琚鎵规祦绋嬪紩鐢紝鏃犳硶缂栬緫");
+ }
+ approvalTemplateMapper.updateById(approvalTemplateDto);
+ approvalTemplateNodeService.remove(
+ new LambdaQueryWrapper<ApprovalTemplateNode>()
+ .eq(ApprovalTemplateNode::getTemplateId, approvalTemplateDto.getId())
+ );
+ approvalTemplateNodeApproverMapper.delete(
+ new LambdaQueryWrapper<ApprovalTemplateNodeApprover>()
+ .eq(ApprovalTemplateNodeApprover::getTemplateId, approvalTemplateDto.getId())
+ );
+ // 淇濆瓨闄勪欢锛堜細鍏堝垹闄ゆ棫闄勪欢锛�
+ List<StorageBlobDTO> storageBlobDTOs = approvalTemplateDto.getStorageBlobDTOs();
+ if (!CollectionUtils.isEmpty(storageBlobDTOs)) {
+ fileUtil.saveStorageAttachment(ApplicationTypeEnum.FILE, RecordTypeEnum.APPROVAL_TEMPLATE, approvalTemplateDto.getId(), storageBlobDTOs);
+ } else {
+ // 濡傛灉鍓嶇浼犵┖鏁扮粍锛屽垹闄ゆ棫闄勪欢
+ fileUtil.deleteStorageAttachmentsByApplicationAndRecordTypeAndRecordId(
+ ApplicationTypeEnum.FILE, RecordTypeEnum.APPROVAL_TEMPLATE, approvalTemplateDto.getId()
+ );
+ }
+ return approvalTemplateNodeService.saveApprovalTemplateNode(
+ approvalTemplateDto.getId(),
+ approvalTemplateDto.getNodes()
+ );
+ }
+
+ @Transactional(rollbackFor = Exception.class)
+ public Boolean delete(List<Long> ids) {
+ if (ids == null || ids.isEmpty()) {
+ return false;
+ }
+ // 妫�鏌ユā鏉挎槸鍚﹁瀹℃壒瀹炰緥寮曠敤
+ for (Long id : ids) {
+ if (isTemplateReferenced(id)) {
+ throw new RuntimeException("瀹℃壒妯℃澘锛圛D: " + id + "锛夊凡琚鎵规祦绋嬪紩鐢紝鏃犳硶鍒犻櫎");
+ }
+ }
+ ApprovalTemplate updateEntity = new ApprovalTemplate();
+ updateEntity.setDeleted(1);
+ LambdaUpdateWrapper<ApprovalTemplate> updateWrapper = Wrappers.lambdaUpdate();
+ updateWrapper.in(ApprovalTemplate::getId, ids)
+ .eq(ApprovalTemplate::getDeleted, 0);
+
+ int rows = approvalTemplateMapper.update(updateEntity, updateWrapper);
+ return rows == ids.size();
+ }
+
+ @Override
+ public List<ApprovalTemplateVo> listApprovalTemplateVo(Integer type) {
+ List<ApprovalTemplate> templateList = this.list(
+ new LambdaQueryWrapper<ApprovalTemplate>()
+ .eq(ApprovalTemplate::getDeleted, 0)
+ .eq(ApprovalTemplate::getEnabled, 1)
+ .notIn(ApprovalTemplate::getBusinessType, List.of(5L, 6L, 7L))
+ .orderByDesc(ApprovalTemplate::getTemplateType)
+ .orderByDesc(ApprovalTemplate::getId)
+ );
+ if (CollUtil.isEmpty(templateList)) {
+ return Collections.emptyList();
+ }
+
+ List<ApprovalTemplateVo> templateVos = templateList.stream()
+ .map(template -> {
+ ApprovalTemplateVo templateVo = new ApprovalTemplateVo();
+ BeanUtils.copyProperties(template, templateVo);
+ return templateVo;
+ })
+ .collect(Collectors.toList());
+ fillTemplateVoNodes(templateVos);
+ return templateVos;
+ }
+
+ @Override
+ public ApprovalTemplateVo getApprovalTemplateVoById(Long id) {
+ if (id == null) {
+ throw new IllegalArgumentException("鍙傛暟 id 涓嶈兘涓虹┖");
+ }
+
+ ApprovalTemplate template = this.getOne(
+ new LambdaQueryWrapper<ApprovalTemplate>()
+ .eq(ApprovalTemplate::getId, id)
+ .eq(ApprovalTemplate::getDeleted, 0)
+ );
+ if (template == null) {
+ throw new IllegalArgumentException("妯℃澘涓嶅瓨鍦�");
+ }
+
+ List<ApprovalTemplateNode> nodeList = approvalTemplateNodeService.list(
+ new LambdaQueryWrapper<ApprovalTemplateNode>()
+ .eq(ApprovalTemplateNode::getTemplateId, id)
+ .orderByAsc(ApprovalTemplateNode::getLevelNo)
+ );
+
+ List<ApprovalTemplateNodeApprover> approverList = approvalTemplateNodeApproverMapper.selectList(
+ new LambdaQueryWrapper<ApprovalTemplateNodeApprover>()
+ .eq(ApprovalTemplateNodeApprover::getTemplateId, id)
+ .eq(ApprovalTemplateNodeApprover::getDeleted, 0L)
+ );
+
+ Map<Long, List<ApprovalTemplateNode>> nodeMap = nodeList.stream()
+ .collect(Collectors.groupingBy(ApprovalTemplateNode::getTemplateId));
+
+ Map<Long, List<ApprovalTemplateNodeApprover>> approverMap = approverList.stream()
+ .collect(Collectors.groupingBy(ApprovalTemplateNodeApprover::getNodeId));
+
+ return buildTemplateVo(template, nodeMap, approverMap);
+ }
+
+ /**
+ * 鎵归噺濉厖妯℃澘鑺傜偣鍙婅妭鐐瑰鎵逛汉锛岄伩鍏嶅惊鐜煡搴撱��
+ */
+ private void fillTemplateVoNodes(List<ApprovalTemplateVo> templateVos) {
+ if (CollUtil.isEmpty(templateVos)) {
+ return;
+ }
+
+ List<Long> templateIds = templateVos.stream()
+ .map(ApprovalTemplateVo::getId)
+ .collect(Collectors.toList());
+
+ List<ApprovalTemplateNode> nodeList = approvalTemplateNodeService.list(
+ new LambdaQueryWrapper<ApprovalTemplateNode>()
+ .in(ApprovalTemplateNode::getTemplateId, templateIds)
+ .orderByAsc(ApprovalTemplateNode::getLevelNo)
+ );
+
+ List<ApprovalTemplateNodeApprover> approverList = approvalTemplateNodeApproverMapper.selectList(
+ new LambdaQueryWrapper<ApprovalTemplateNodeApprover>()
+ .in(ApprovalTemplateNodeApprover::getTemplateId, templateIds)
+ .eq(ApprovalTemplateNodeApprover::getDeleted, 0L)
+ );
+
+ Map<Long, List<ApprovalTemplateNode>> nodeMap = nodeList.stream()
+ .collect(Collectors.groupingBy(ApprovalTemplateNode::getTemplateId));
+
+ Map<Long, List<ApprovalTemplateNodeApprover>> approverMap = approverList.stream()
+ .collect(Collectors.groupingBy(ApprovalTemplateNodeApprover::getNodeId));
+
+ templateVos.forEach(templateVo -> templateVo.setNodes(
+ nodeMap.getOrDefault(templateVo.getId(), Collections.emptyList())
+ .stream()
+ .sorted(Comparator.comparing(
+ ApprovalTemplateNode::getLevelNo,
+ Comparator.nullsLast(Integer::compareTo)
+ ))
+ .map(node -> buildNodeVo(node, approverMap))
+ .collect(Collectors.toList())
+ ));
+ }
+
+ private ApprovalTemplateVo buildTemplateVo(ApprovalTemplate template,
+ Map<Long, List<ApprovalTemplateNode>> nodeMap,
+ Map<Long, List<ApprovalTemplateNodeApprover>> approverMap) {
+ ApprovalTemplateVo templateVo = new ApprovalTemplateVo();
+ BeanUtils.copyProperties(template, templateVo);
+
+ List<ApprovalTemplateNodeVo> nodeVos = nodeMap
+ .getOrDefault(template.getId(), Collections.emptyList())
+ .stream()
+ .sorted(Comparator.comparing(
+ ApprovalTemplateNode::getLevelNo,
+ Comparator.nullsLast(Integer::compareTo)
+ ))
+ .map(node -> buildNodeVo(node, approverMap))
+ .collect(Collectors.toList());
+
+ templateVo.setNodes(nodeVos);
+ // 鏌ヨ闄勪欢
+ templateVo.setStorageBlobDTOs(
+ fileUtil.getStorageBlobVOsByApplicationAndRecordTypeAndRecordId(
+ ApplicationTypeEnum.FILE, RecordTypeEnum.APPROVAL_TEMPLATE, template.getId()
+ )
+ );
+ return templateVo;
+ }
+
+ private ApprovalTemplateNodeVo buildNodeVo(ApprovalTemplateNode node,
+ Map<Long, List<ApprovalTemplateNodeApprover>> approverMap) {
+ ApprovalTemplateNodeVo nodeVo = new ApprovalTemplateNodeVo();
+ BeanUtils.copyProperties(node, nodeVo);
+
+ List<ApprovalTemplateNodeApproverVo> approverVos = approverMap
+ .getOrDefault(node.getId(), Collections.emptyList())
+ .stream()
+ .sorted(Comparator.comparing(
+ ApprovalTemplateNodeApprover::getSortNo,
+ Comparator.nullsLast(Integer::compareTo)
+ ))
+ .map(this::buildApproverVo)
+ .collect(Collectors.toList());
+
+ nodeVo.setApprovers(approverVos);
+ return nodeVo;
+ }
+
+ private ApprovalTemplateNodeApproverVo buildApproverVo(ApprovalTemplateNodeApprover approver) {
+ ApprovalTemplateNodeApproverVo approverVo = new ApprovalTemplateNodeApproverVo();
+ BeanUtils.copyProperties(approver, approverVo);
+ return approverVo;
+ }
+
+ /**
+ * 妫�鏌ュ鎵规ā鏉挎槸鍚﹁瀹℃壒瀹炰緥寮曠敤
+ * @param templateId 妯℃澘ID
+ * @return true 琛ㄧず琚紩鐢紝false 琛ㄧず鏈寮曠敤
+ */
+ private boolean isTemplateReferenced(Long templateId) {
+ if (templateId == null) {
+ return false;
+ }
+ Long count = approvalInstanceMapper.selectCount(
+ new LambdaQueryWrapper<ApprovalInstance>()
+ .eq(ApprovalInstance::getTemplateId, templateId)
+ .eq(ApprovalInstance::getDeleted, 0)
+ );
+ return count != null && count > 0;
+ }
+}
--
Gitblit v1.9.3