소스 검색

状态节点映射

chenxiaofei 1 개월 전
부모
커밋
178a6caee5
1개의 변경된 파일66개의 추가작업 그리고 12개의 파일을 삭제
  1. 66 12
      sckw-modules/sckw-transport/src/main/java/com/sckw/transport/service/KwtWaybillOrderV1Service.java

+ 66 - 12
sckw-modules/sckw-transport/src/main/java/com/sckw/transport/service/KwtWaybillOrderV1Service.java

@@ -5496,9 +5496,7 @@ public class KwtWaybillOrderV1Service {
         // 获取时间节点,并按前端五步序号排序(映射写入 orderStatus / orderStatusName)
         // 获取时间节点,并按前端五步序号排序(映射写入 orderStatus / orderStatusName)
         List<WaybillOrderNodeVo.WaybillOrderNode> nodeList = getWaybillOrderNodes(voList);
         List<WaybillOrderNodeVo.WaybillOrderNode> nodeList = getWaybillOrderNodes(voList);
         log.info("查询运单节点轨迹,时间节点:{}", JSON.toJSONString(nodeList));
         log.info("查询运单节点轨迹,时间节点:{}", JSON.toJSONString(nodeList));
-        // 将原始运单状态映射为前端五步时间轴阶段(1-5),并更新节点的状态码和名称
-        applyTimelinePhaseFromWaybillStatus(nodeList);
-        // 对映射后的节点列表按阶段去重,保留每个阶段最早的一条记录
+        // 按前端五步时间轴阶段去重,取满足状态中的最小原始状态对应时间
         nodeList = dedupeWaybillOrderNodesByStatus(nodeList);
         nodeList = dedupeWaybillOrderNodesByStatus(nodeList);
         nodeList = nodeList.stream()
         nodeList = nodeList.stream()
                 .sorted(Comparator.comparing(WaybillOrderNodeVo.WaybillOrderNode::getOrderStatus))
                 .sorted(Comparator.comparing(WaybillOrderNodeVo.WaybillOrderNode::getOrderStatus))
@@ -5590,20 +5588,76 @@ public class KwtWaybillOrderV1Service {
             return nodeList;
             return nodeList;
         }
         }
         return nodeList.stream()
         return nodeList.stream()
-                .filter(node -> node.getOrderStatus() != null)
-                .collect(Collectors.toMap(
-                        WaybillOrderNodeVo.WaybillOrderNode::getOrderStatus,
-                        Function.identity(),
-                        (a, b) -> {
-                            Date ta = parseWaybillNodeCreateTime(a.getCreateTime());
-                            Date tb = parseWaybillNodeCreateTime(b.getCreateTime());
-                            return !ta.after(tb) ? a : b;
-                        }))
+                .filter(node -> Objects.nonNull(node.getOrderStatus()))
+                .collect(Collectors.groupingBy(node -> WaybillTimelinePhaseEnum.resolve(node.getOrderStatus())
+                        .map(WaybillTimelinePhaseEnum::getPhaseOrder)
+                        .orElse(node.getOrderStatus())))
                 .values()
                 .values()
                 .stream()
                 .stream()
+                .map(KwtWaybillOrderV1Service::selectMinStatusEarliestNode)
+                .filter(Objects::nonNull)
                 .collect(Collectors.toList());
                 .collect(Collectors.toList());
     }
     }
 
 
+    /**
+     * 从同一前端时间轴阶段的节点列表中,筛选出用于展示的单一节点。
+     * <p>
+     * 处理逻辑:
+     * 1. 找出列表中原始状态码(orderStatus)最小的节点集合(通常代表该阶段最早触发的业务状态)。
+     * 2. 在最小状态码的节点中,选取创建时间(createTime)最早的一个节点。
+     * 3. 将选中节点的 orderStatus 和 orderStatusName 映射为前端时间轴所需的阶段序号和阶段名称。
+     * </p>
+     *
+     * @param nodes 属于同一前端展示阶段的运单节点列表
+     * @return 筛选后的单个节点对象,若列表为空或无有效数据则返回 null
+     */
+    private static WaybillOrderNodeVo.WaybillOrderNode selectMinStatusEarliestNode(
+            List<WaybillOrderNodeVo.WaybillOrderNode> nodes) {
+        // 1. 空值校验
+        if (CollectionUtils.isEmpty(nodes)) {
+            log.debug("selectMinStatusEarliestNode: 节点列表为空,返回 null");
+            return null;
+        }
+        
+        // 2. 提取最小原始状态码
+        // 在同一阶段映射下,可能存在多个原始业务状态,取数值最小的作为基准(通常代表初始状态)
+        Integer minStatus = nodes.stream()
+                .map(WaybillOrderNodeVo.WaybillOrderNode::getOrderStatus)
+                .filter(Objects::nonNull)
+                .min(Integer::compareTo)
+                .orElse(null);
+                
+        if (Objects.isNull(minStatus)) {
+            log.warn("selectMinStatusEarliestNode: 无法从节点列表中提取有效的最小状态码,节点数量: {}", nodes.size());
+            return null;
+        }
+        log.debug("selectMinStatusEarliestNode: 提取到最小状态码: {}", minStatus);
+        
+        // 3. 筛选具有最小状态码且创建时间最早的节点
+        WaybillOrderNodeVo.WaybillOrderNode selected = nodes.stream()
+                .filter(node -> Objects.equals(node.getOrderStatus(), minStatus))
+                .min(Comparator.comparing(node -> parseWaybillNodeCreateTime(node.getCreateTime())))
+                .orElse(null);
+                
+        if (Objects.isNull(selected)) {
+            log.warn("selectMinStatusEarliestNode: 状态码为 {} 的节点中未找到有效创建时间的节点", minStatus);
+            return null;
+        }
+        log.debug("selectMinStatusEarliestNode: 选中节点 ID: {}, 状态: {}, 创建时间: {}", 
+                selected.getId(), selected.getOrderStatus(), selected.getCreateTime());
+        
+        // 4. 映射前端时间轴阶段信息
+        // 将原始业务状态转换为前端展示用的阶段序号(phaseOrder)和阶段名称(phaseLabel)
+        WaybillTimelinePhaseEnum.resolve(minStatus).ifPresent(phase -> {
+            log.debug("selectMinStatusEarliestNode: 映射前端阶段,原始状态: {} -> 阶段序号: {}, 阶段名称: {}", 
+                    minStatus, phase.getPhaseOrder(), phase.getPhaseLabel());
+            selected.setOrderStatus(phase.getPhaseOrder());
+            selected.setOrderStatusName(phase.getPhaseLabel());
+        });
+        
+        return selected;
+    }
+
     private static Date parseWaybillNodeCreateTime(String createTime) {
     private static Date parseWaybillNodeCreateTime(String createTime) {
         if (org.apache.commons.lang3.StringUtils.isBlank(createTime)) {
         if (org.apache.commons.lang3.StringUtils.isBlank(createTime)) {
             return new Date(0L);
             return new Date(0L);