소스 검색

Merge remote-tracking branch 'origin/dev' into dev

cr 18 시간 전
부모
커밋
38082b3519

+ 31 - 0
blade-service-api/blade-manager-api/src/main/java/org/springblade/manager/feign/WbsTreeContractExtendClient.java

@@ -0,0 +1,31 @@
+package org.springblade.manager.feign;
+
+import org.springblade.manager.entity.WbsTreeContract;
+import org.springblade.manager.entity.WbsTreeContractExtend;
+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 WbsTreeContractExtendClient {
+
+    /**
+     * 接口前缀
+     */
+    String API_PREFIX = "/api/manager/WbsTreeContractExtend";
+
+    @PostMapping(API_PREFIX + "/getByPKeyId")
+    List<WbsTreeContractExtend> getByPKeyId(@RequestBody WbsTreeContract wbsTreeContract);
+
+    @PostMapping(API_PREFIX + "/save")
+    Boolean save(@RequestBody WbsTreeContractExtend wbsTreeContractExtend);
+    @PostMapping(API_PREFIX + "/saveList")
+    Boolean saveList(@RequestBody List<WbsTreeContractExtend> wbsTreeContractExtends);
+
+    @PostMapping(API_PREFIX + "/getByAncestorsPId")
+    List<WbsTreeContractExtend> getByAncestorsPid(String ancestorsPid);
+}

+ 48 - 0
blade-service/blade-business/src/main/java/org/springblade/business/controller/InformationWriteQueryController.java

@@ -119,6 +119,9 @@ public class InformationWriteQueryController extends BladeController {
     private final ContractClient contractClient;
 
     private final WbsTreeContractClient wbsTreeContractClient;
+
+    private final WbsTreeContractExtendClient wbsTreeContractExtendClient;
+
     private final WbsTreeContractOldHtmlClient wbsTreeContractOldHtmlClient;
 
     private final WbsTreePrivateClient wbsTreePrivateClient;
@@ -2048,6 +2051,8 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
     if (("1").equals(vo.getCopyType())) {
         //选中节点
         WbsTreeContract needCopyNode = this.wbsTreeContractClient.getContractNodeByPrimaryKeyId(vo.getNeedCopyPrimaryKeyId());
+        //获取扩展表信息,同时复制扩展表信息  要考虑复制节点下存在其他子级节点
+        List<WbsTreeContractExtend> wbsTreeContractExtend = wbsTreeContractExtendClient.getByPKeyId(needCopyNode);
 
         /*结果集-节点表*/
         List<WbsTreeContract> saveList = new ArrayList<>();
@@ -2160,6 +2165,17 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
                     logger.info("以下元素表没有获取到对应实体表数据,已跳过 ===> 表pKeyId:[{}]", StringUtils.join(continuePkeyIds, ","));
                 }
             }
+            //根据旧节点 pkid 获取新节点pkid
+            if(wbsTreeContractExtend != null){
+                wbsTreeContractExtend.forEach(f->{
+                    f.setPKeyId(oldPKeyIdToNewPKeyIdMap.get(f.getPKeyId()));
+                });
+                List<WbsTreeContractExtend> collect = wbsTreeContractExtend.stream().filter(f -> f.getPKeyId() != null).collect(Collectors.toList());
+                if(!collect.isEmpty()){
+                    //排除没有扩展表记录的节点
+                    Boolean b = wbsTreeContractExtendClient.saveList(collect);
+                }
+            }
             // 节点+表节点
             for (WbsTreeContract nodeOld : nodeChildAll) {
                 //新节点
@@ -2379,6 +2395,8 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
             }
 
             WbsTreeContract needCopyNodeRoot = this.wbsTreeContractClient.getContractNodeByPrimaryKeyId(vo.getNeedCopyPrimaryKeyId());
+            //获取当前节点扩展表
+            List<WbsTreeContractExtend> contractExtends = wbsTreeContractExtendClient.getByPKeyId(needCopyNodeRoot);
             if (needCopyNodeRoot != null) {
                 /*缓存需要复制的节点、表信息*/
                 Map<String, List<WbsTreeContract>> needCopyNodeAndTabMap = new HashMap<>();
@@ -2556,6 +2574,9 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
                 if (nodes.size() > 0) {
                     /*复制formulaOption*/
                     this.copyFormulaOptions(nodes, peerMap);
+                    /*复制扩展表数据*/
+                    List<WbsTreeContractExtend> saveContractExtend = this.copyContractExtend(contractExtends, peerMap);
+                    wbsTreeContractExtendClient.saveList(saveContractExtend);
                 }
                 if (row) {
                     //更新redis缓存
@@ -2593,6 +2614,33 @@ public R<Boolean> copyContractTreeNode(@RequestBody CopyContractTreeNodeVO vo) {
     return R.fail("操作失败");
 }
 
+    /**
+     * 复制合同段扩展表
+     * @param contractExtends 旧节点扩展表信息
+     * @param map 新节点与旧节点 映射关系
+     * */
+    private List<WbsTreeContractExtend> copyContractExtend(List<WbsTreeContractExtend> contractExtends, Map<Long, Long> map) {
+        List<WbsTreeContractExtend> wbsTreeContractExtends = new ArrayList<>();
+        contractExtends.forEach(f->{
+            //根基旧节点查询新节点信息,一个旧节点可能存在多个新节点数据
+            List<Long> cities = map.entrySet()
+                    .stream()
+                    .filter(entry -> f.getPKeyId().equals(entry.getValue()))
+                    .map(Map.Entry::getKey)
+                    .collect(Collectors.toList());
+            if(CollectionUtil.isNotEmpty(cities)){
+                cities.forEach(c->{
+                    WbsTreeContractExtend wbsTreeContractExtend = BeanUtil.copyProperties(f, WbsTreeContractExtend.class);
+                    if(wbsTreeContractExtend != null){
+                        wbsTreeContractExtend.setPKeyId(c);
+                        wbsTreeContractExtends.add(wbsTreeContractExtend);
+                    }
+                });
+            }
+        });
+        return wbsTreeContractExtends;
+    }
+
 @Async
 public void copyFormulaOptions(List<WbsTreeContract> saveList, Map<Long, Long> peerMap) {
     if (peerMap.size() > 0) {

+ 14 - 0
blade-service/blade-manager/src/main/java/com/mixsmart/utils/CustomFunction.java

@@ -17,6 +17,7 @@ import org.springblade.core.tool.utils.*;
 import org.springblade.manager.bean.SpringContextHolder;
 import org.springblade.manager.dto.ParamElements;
 import org.springblade.manager.entity.WbsTreeContract;
+import org.springblade.manager.utils.NumberStringSubtraction;
 import org.springblade.manager.utils.RandomNumberHolder;
 import org.springframework.jdbc.core.JdbcTemplate;
 
@@ -2252,6 +2253,7 @@ public class CustomFunction {
         List<Object> list = obj2List(obj);
         return list.parallelStream().filter(StringUtils::isNotEmpty).collect(Collectors.toList());
     }
+    //obj转数组,不做任何额外的处理
     public static List<Object> obj3ListNe(Object obj) {
         List<Object> list = obj3List(obj);
         return list.parallelStream().filter(StringUtils::isNotEmpty).collect(Collectors.toList());
@@ -3297,4 +3299,16 @@ public class CustomFunction {
         BigDecimal remainder = number.remainder(BigDecimal.valueOf(2));
         return remainder.compareTo(BigDecimal.ZERO) == 0;
     }
+
+    /**
+     * 字符串拆分计算
+     * @param s
+     * @param s1
+     * @return
+     */
+    public static List<Integer> strSplitDiff(Object s,Object s1){
+        List<Object> datas = obj3ListNe(s);
+        List<Object> data1 = obj3ListNe(s1);
+        return NumberStringSubtraction.calculateDifference(datas.get(0).toString(), data1.get(0).toString());
+    }
 }

+ 59 - 0
blade-service/blade-manager/src/main/java/org/springblade/manager/feign/WbsTreeContractExtendClientImpl.java

@@ -0,0 +1,59 @@
+package org.springblade.manager.feign;
+
+import com.baomidou.mybatisplus.core.toolkit.Wrappers;
+import lombok.AllArgsConstructor;
+import org.springblade.manager.entity.WbsTreeContract;
+import org.springblade.manager.entity.WbsTreeContractExtend;
+import org.springblade.manager.service.IWbsTreeContractService;
+import org.springblade.manager.service.WbsTreeContractExtendService;
+import org.springframework.web.bind.annotation.RestController;
+
+import javax.annotation.Resource;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+@RestController
+@AllArgsConstructor
+public class WbsTreeContractExtendClientImpl implements WbsTreeContractExtendClient {
+
+    @Resource
+    private WbsTreeContractExtendService wbsTreeContractExtendService;
+    @Resource
+    private IWbsTreeContractService wbsTreeContractService;
+
+    @Override
+    public List<WbsTreeContractExtend> getByPKeyId(WbsTreeContract wbsTreeContract) {
+        //查询指定节点下的其他节点 不查询表单
+        List<WbsTreeContract> list = wbsTreeContractService.list(Wrappers.<WbsTreeContract>lambdaQuery()
+                .eq(WbsTreeContract::getContractId, wbsTreeContract.getContractId())
+                .eq(WbsTreeContract::getType, 1)
+                .likeRight(WbsTreeContract::getAncestorsPId, wbsTreeContract.getAncestorsPId())
+        );
+        Set<Long> collect = list.stream().map(WbsTreeContract::getPKeyId).collect(Collectors.toSet());
+        //可能当前节点下没有子节点了,把当前节点加进去
+        collect.add(wbsTreeContract.getPKeyId());
+
+        return wbsTreeContractExtendService.listByIds(collect);
+    }
+
+    @Override
+    public Boolean save(WbsTreeContractExtend wbsTreeContractExtend) {
+        return wbsTreeContractExtendService.save(wbsTreeContractExtend);
+    }
+
+    @Override
+    public Boolean saveList(List<WbsTreeContractExtend> wbsTreeContractExtends) {
+        return wbsTreeContractExtendService.saveBatch(wbsTreeContractExtends);
+    }
+
+    @Override
+    public List<WbsTreeContractExtend> getByAncestorsPid(String ancestorsPid) {
+        //只复制节点 不复制表单
+
+        return wbsTreeContractExtendService.list(Wrappers.<WbsTreeContractExtend>lambdaQuery()
+                .eq(WbsTreeContractExtend::getIsDeleted,0)
+                .in(WbsTreeContractExtend::getPKeyId,Arrays.asList(ancestorsPid.split(","))));
+    }
+}

+ 104 - 0
blade-service/blade-manager/src/main/java/org/springblade/manager/utils/NumberStringSubtraction.java

@@ -0,0 +1,104 @@
+package org.springblade.manager.utils;
+
+import java.util.*;
+
+/**
+ * @author LHB
+ * 字符串拆分
+ */
+public class NumberStringSubtraction {
+
+    public static List<Integer> calculateDifference(String a, String b) {
+        // 分割字符串为数字列表
+        List<Integer> aNumbers = parseNumbers(a);
+        List<Integer> bNumbers = parseNumbers(b);
+
+        List<Integer> result = new ArrayList<>();
+
+        // 情况1:数字数量一致,一一对应计算
+        if (aNumbers.size() == bNumbers.size()) {
+            for (int i = 0; i < aNumbers.size(); i++) {
+                result.add(aNumbers.get(i) - bNumbers.get(i));
+            }
+        }
+        // 情况2:数字数量不一致,b数字可重复使用
+        else {
+            // 对b数字列表排序,便于查找
+            List<Integer> sortedBNumbers = new ArrayList<>(bNumbers);
+            Collections.sort(sortedBNumbers);
+
+            for (int aNum : aNumbers) {
+                // 在b数字中找到最接近且小于等于aNum的数字
+                int bestB = findClosestWithPreference(aNum, sortedBNumbers);
+                result.add(aNum - bestB);
+            }
+        }
+
+        return result;
+    }
+
+    private static int findClosestWithPreference(int aNum, List<Integer> sortedBNumbers) {
+        // 如果b列表为空,返回0
+        if (sortedBNumbers.isEmpty()) {
+            return 0;
+        }
+
+        // 找到所有与aNum差值最小的数字
+        List<Integer> closestNumbers = new ArrayList<>();
+        int minDiff = Integer.MAX_VALUE;
+
+        for (int bNum : sortedBNumbers) {
+            int diff = Math.abs(aNum - bNum);
+            if (diff < minDiff) {
+                minDiff = diff;
+                closestNumbers.clear();
+                closestNumbers.add(bNum);
+            } else if (diff == minDiff) {
+                closestNumbers.add(bNum);
+            }
+        }
+
+        // 如果只有一个最接近的数字,直接返回
+        if (closestNumbers.size() == 1) {
+            return closestNumbers.get(0);
+        }
+
+        // 如果有多个相同接近的数字,优先选择小于aNum的
+        List<Integer> greaterThanA = new ArrayList<>();
+        for (int num : closestNumbers) {
+            if (num < aNum) {
+                greaterThanA.add(num);
+            }
+        }
+
+        // 如果有大于aNum的数字,返回其中最小的
+        if (!greaterThanA.isEmpty()) {
+            Collections.sort(greaterThanA);
+            return greaterThanA.get(0);
+        }
+
+        // 如果没有大于aNum的数字,返回最大的那个(最接近但小于等于aNum的)
+        Collections.sort(closestNumbers);
+        return closestNumbers.get(closestNumbers.size() - 1);
+    }
+
+    private static List<Integer> parseNumbers(String str) {
+        List<Integer> numbers = new ArrayList<>();
+        if (str == null || str.trim().isEmpty()) {
+            return numbers;
+        }
+
+        // 支持多种分隔符:/ , 空格 \
+        String[] parts = str.split("[\\\\/,,、\\s]+");
+        for (String part : parts) {
+            try {
+                numbers.add(Integer.parseInt(part.trim()));
+            } catch (NumberFormatException e) {
+                // 忽略非数字部分
+                System.err.println("警告: 忽略非数字部分: " + part);
+            }
+        }
+
+        return numbers;
+    }
+}