Эх сурвалжийг харах

查询钢坯装运单时维护车次序号跟总车次序号

lingpeng.li 1 сар өмнө
parent
commit
def2945fa9

+ 19 - 0
zgztBus/jeecg-boot-base-core/src/main/java/org/jeecg/common/util/DateUtils.java

@@ -861,4 +861,23 @@ public class DateUtils extends PropertyEditorSupport {
         return calendar.getTime();
     }
 
+    // 获取某天00:00:00
+    public static Date getStartOfDay(Date date) {
+        Calendar calendar = Calendar.getInstance();
+        calendar.setTime(date);
+        calendar.set(Calendar.HOUR_OF_DAY, 0);
+        calendar.set(Calendar.MINUTE, 0);
+        calendar.set(Calendar.SECOND, 0);
+        calendar.set(Calendar.MILLISECOND, 0);
+        return calendar.getTime();
+    }
+
+    // 获取下一天00:00:00
+    public static Date addDays(Date date, int days) {
+        Calendar calendar = Calendar.getInstance();
+        calendar.setTime(date);
+        calendar.add(Calendar.DATE, days);
+        return calendar.getTime();
+    }
+
 }

+ 4 - 1
zgztBus/jeecg-module-sbm/src/main/java/org/jeecg/modules/billet/storageBill/controller/StorageBillController.java

@@ -222,7 +222,10 @@ public class StorageBillController extends JeecgController<StorageBill, IStorage
 		List<StorageBill> pageRecords = (fromIndex >= filteredRecords.size()) ?
 				Collections.emptyList() : filteredRecords.subList(fromIndex, toIndex);
 
-		// 8. 封装分页数据
+		// 8. 遍历 StorageBill 添加车次编号、总车次编号、更新交班记录
+		storageBillService.fillCarNumbersAndShiftInfo(pageRecords);
+
+		// 9. 封装分页数据
 		Page<StorageBill> pageList = new Page<>(pageNo, pageSize);
 		pageList.setRecords(pageRecords);
 		pageList.setTotal(total);

+ 1 - 0
zgztBus/jeecg-module-sbm/src/main/java/org/jeecg/modules/billet/storageBill/service/IStorageBillService.java

@@ -96,5 +96,6 @@ public interface IStorageBillService extends IService<StorageBill> {
 
     StorageCenterHeatNoInvoicingVO storageCenterInvoicingByHeatNo(String heatNo);
 
+    void fillCarNumbersAndShiftInfo(List<StorageBill> bills);
 
 }

+ 120 - 146
zgztBus/jeecg-module-sbm/src/main/java/org/jeecg/modules/billet/storageBill/service/impl/StorageBillServiceImpl.java

@@ -12,6 +12,7 @@ import com.google.common.collect.Maps;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.commons.collections.CollectionUtils;
 import org.apache.commons.lang.StringUtils;
+import org.apache.commons.lang.time.DateFormatUtils;
 import org.jeecg.common.util.DateUtils;
 import org.jeecg.common.util.oConvertUtils;
 import org.jeecg.modules.actualControl.billetActual.billetActual.entity.BilletBasicInfo;
@@ -5575,155 +5576,128 @@ public class StorageBillServiceImpl extends ServiceImpl<StorageBillMapper, Stora
             storageCenterHeatNoInvoicingVO.setRollOutShippDetails(rollOutHeatNo);
         }
 
-//        if (groupedByBelongTable.containsKey("stacking_and_loading_vehicles")) {
-//
-//            List<BilletBasicInfo> billetBasicInfos = groupedByBelongTable.get("stacking_and_loading_vehicles");
-//
-//            // 计算总重量 & 总条数
-//            BigDecimal totalBlankOutput = billetBasicInfos.stream()
-//                    .map(BilletBasicInfo::getBilletWeight)
-//                    .filter(Objects::nonNull)
-//                    .map(BigDecimal::valueOf)
-//                    .reduce(BigDecimal.ZERO, BigDecimal::add);
-//
-//            stackHeatNo.setTotalAmount(billetBasicInfos.size());
-//            stackHeatNo.setTotalWeight(totalBlankOutput);
-//
-//            // 按照 getLength 分组
-//            Map<Integer, List<BilletBasicInfo>> groupedByLength = billetBasicInfos.stream()
-//                    .filter(b -> b.getLength() != null) // 先过滤掉 null,防止 NPE
-//                    .collect(Collectors.groupingBy(BilletBasicInfo::getLength));
-//
-//            List<StorageCenterHeatNoDetailVO.SizeDetail> sizeDetailsList = groupedByLength.entrySet().stream()
-//                    .map(entry -> {
-//                        Integer length = entry.getKey();
-//                        List<BilletBasicInfo> billets = entry.getValue();
-//
-//                        // 计算 weight 总和
-//                        BigDecimal totalWeight = billets.stream()
-//                                .map(BilletBasicInfo::getBilletWeight)
-//                                .filter(Objects::nonNull)
-//                                .map(BigDecimal::valueOf)
-//                                .reduce(BigDecimal.ZERO, BigDecimal::add);
-//
-//                        // 创建 SizeDetail
-//                        StorageCenterHeatNoDetailVO.SizeDetail sizeDetail = new StorageCenterHeatNoDetailVO.SizeDetail();
-//                        sizeDetail.setSize(length);
-//                        sizeDetail.setSizeWeight(totalWeight);
-//                        sizeDetail.setSizeAmount(billets.size());
-//
-//                        return sizeDetail;
-//                    })
-//                    .collect(Collectors.toList());
-//
-//            stackHeatNo.setSizeDetails(sizeDetailsList);
-//
-//
-//            Map<String, List<BilletBasicInfo>> groupedByHeatNoAndBilletNo = billetBasicInfos.stream()
-//                    .filter(b -> b.getHeatNo() != null && b.getBilletNo() != null) // 先过滤掉 null,防止 NPE
-//                    .collect(Collectors.groupingBy(b -> b.getHeatNo() + "_" + b.getBilletNo()));
-//
-//
-//            List<StorageCenterHeatNoDetailVO.StackingVehiclesDetail> stackingVehiclesDetails = new ArrayList<>();
-//
-//            for (Map.Entry<String, List<BilletBasicInfo>> entry : groupedByHeatNoAndBilletNo.entrySet()) {
-//                String key = entry.getKey();  // 获取拼接的 key
-//                String[] parts = key.split("_", 2); // 以 "_" 分割 key,限制最多分割 2 部分
-//                String splitHeatNo = parts.length > 0 ? parts[0] : "Unknown";   // 获取 HeatNo
-//                String billetNo = parts.length > 1 ? parts[1] : "Unknown"; // 获取 BilletNo
-//
-//                List<BilletBasicInfo> billets = entry.getValue();
-//                if (billets == null || billets.isEmpty()) {
-//                    continue; // 避免空数据
-//                }
-//
-//                LambdaQueryWrapper<StackingAndLoadingVehicles> stackingLambdaQueryWrapper = new LambdaQueryWrapper<>();
-//
-//                stackingLambdaQueryWrapper
-//                        .like(StackingAndLoadingVehicles::getHeatNo, splitHeatNo)  // heatNo 模糊匹配
-//                        .like(StackingAndLoadingVehicles::getBilletNos, billetNo); // billetNos 模糊匹配
-//
-//                List<StackingAndLoadingVehicles> stackingAndLoadingVehicles = stackingAndLoadingVehiclesMapper.selectList(stackingLambdaQueryWrapper);
-//
-//                // 默认值
-//                String stackAddr = "未知";
-//                String layer = "未知";
-//                String address = "未知";
-//
-//                if (!stackingAndLoadingVehicles.isEmpty()) {
-//                    stackAddr = stackingAndLoadingVehicles.get(0).getStackAddr();
-//                    layer = stackingAndLoadingVehicles.get(0).getLayer();
-//                    address = stackingAndLoadingVehicles.get(0).getAddress();
-////                    size = stackingAndLoadingVehicles.get(0).getSize();
-//                }
-//
-//                Integer size = Optional.ofNullable(billets.get(0).getLength()).orElse(0); // 避免 NullPointerException
-//                String spec = Optional.ofNullable(billets.get(0).getSpec()).orElse("Unknown"); // 避免 null 赋值
-//
-//                // 计算 weight 总和
-//                BigDecimal totalWeight = billets.stream()
-//                        .map(BilletBasicInfo::getBilletWeight)
-//                        .filter(Objects::nonNull)
-//                        .map(BigDecimal::valueOf)
-//                        .reduce(BigDecimal.ZERO, BigDecimal::add);
-//
-//                // 创建 RollChargeDetail
-//                StorageCenterHeatNoDetailVO.StackingVehiclesDetail stackingVehiclesDetail = new StorageCenterHeatNoDetailVO.StackingVehiclesDetail();
-//                stackingVehiclesDetail.setSize(size);
-//                stackingVehiclesDetail.setSpec(spec);
-//                stackingVehiclesDetail.setWeight(totalWeight);
-//                stackingVehiclesDetail.setAmount(billets.size());
-//                stackingVehiclesDetail.setStackAddr(stackAddr);
-//                stackingVehiclesDetail.setLayer(layer);
-//                stackingVehiclesDetail.setAddress(address);
-//
-//                stackingVehiclesDetails.add(stackingVehiclesDetail);
-//
-//            }
-//
-//            // 先对 stackDetails 进行分组
-//            Map<String, StorageCenterHeatNoDetailVO.StackingVehiclesDetail> groupedStackDetails = stackingVehiclesDetails.stream()
-//                    .collect(Collectors.toMap(
-//                            // key: stackAddr + layer + address 作为分组依据
-//                            detail -> detail.getStackAddr() + "_" + detail.getLayer() + "_" + detail.getAddress(),
-//                            // value: 原始数据
-//                            detail -> {
-//                                StorageCenterHeatNoDetailVO.StackingVehiclesDetail newDetail = new StorageCenterHeatNoDetailVO.StackingVehiclesDetail();
-//                                newDetail.setSize(detail.getSize());
-//                                newDetail.setSpec(detail.getSpec());
-//                                newDetail.setAmount(detail.getAmount());
-//                                newDetail.setWeight(detail.getWeight());
-//                                newDetail.setStackAddr(detail.getStackAddr());
-//                                newDetail.setLayer(detail.getLayer());
-//                                newDetail.setAddress(detail.getAddress());
-//                                return newDetail;
-//                            },
-//                            // 合并逻辑:累加 amount 和 weight
-//                            (existing, newDetail) -> {
-//                                existing.setAmount(existing.getAmount() + newDetail.getAmount());
-//                                existing.setWeight(existing.getWeight().add(newDetail.getWeight()));
-//                                return existing;
-//                            }
-//                    ));
-//
-//            // 转换为 List,并按照 layer 和 address 进行排序
-//            List<StorageCenterHeatNoDetailVO.StackingVehiclesDetail> mergedStackDetails = groupedStackDetails.values().stream()
-//                    .sorted(Comparator.comparing(StorageCenterHeatNoDetailVO.StackingVehiclesDetail::getLayer)
-//                            .thenComparing(StorageCenterHeatNoDetailVO.StackingVehiclesDetail::getAddress)) // 先按 layer,再按 address 排序
-//                    .collect(Collectors.toList());// 转换为 List
-//
-//            // 更新 stackHeatNo
-//            stackHeatNo.setStackDetails(mergedStackDetails);
-//
-//            stackHeatNo.setSizeDetails(sizeDetailsList);
-//
-//            storageCenterHeatNoDetailVO.setStackingVehicles(stackHeatNo);
-//
-//        }
-
         return storageCenterHeatNoInvoicingVO;
     }
 
+    public void fillCarNumbersAndShiftInfo(List<StorageBill> bills) {
+        if (CollectionUtils.isEmpty(bills)) return;
+
+        // Step 1: 预提取所有用到的条件组合
+        Set<String> shiftKeys = new HashSet<>();
+        Set<String> billKeys = new HashSet<>();
+        for (StorageBill bill : bills) {
+            Date billDate = DateUtils.getStartOfDay(bill.getCreateTime());
+            String shiftKey = String.join("_", bill.getCcmNo(), bill.getShiftGroup(), bill.getShift(), DateFormatUtils.format(billDate, "yyyy-MM-dd"));
+            shiftKeys.add(shiftKey);
+
+            String billKey = String.join("_", bill.getCcmNo(), bill.getShiftGroup(), bill.getShift(), DateFormatUtils.format(billDate, "yyyy-MM-dd"));
+            billKeys.add(billKey);
+        }
+
+        // Step 2: 批量查询交班记录并缓存
+        List<BilletHotsendChangeShift> shiftList = billetHotsendChangeShiftService.lambdaQuery()
+                .in(BilletHotsendChangeShift::getCcmNo, bills.stream().map(StorageBill::getCcmNo).collect(Collectors.toSet()))
+                .between(BilletHotsendChangeShift::getCreateTime, getMinDate(bills), getMaxDate(bills))
+                .list();
+
+        Map<String, BilletHotsendChangeShift> shiftMap = shiftList.stream()
+                .collect(Collectors.toMap(
+                        s -> String.join("_", s.getCcmNo(), s.getShiftGroup(), s.getShift(), DateFormatUtils.format(DateUtils.getStartOfDay(s.getCreateTime()), "yyyy-MM-dd")),
+                        Function.identity(),
+                        (v1, v2) -> v1 // 取较早的那个记录
+                ));
+
+        // Step 3: 批量查询所有相关的 StorageBill
+        List<StorageBill> allRelatedBills = this.lambdaQuery()
+                .in(StorageBill::getCcmNo, bills.stream().map(StorageBill::getCcmNo).collect(Collectors.toSet()))
+                .between(StorageBill::getCreateTime, getMinDate(bills), getMaxDate(bills))
+                .list();
+
+        // 多级 map 存储 [ccmNo+shiftGroup+shift+licensePlate+day] -> List<StorageBill>
+        Map<String, List<StorageBill>> billGroupMap = allRelatedBills.stream().collect(Collectors.groupingBy(b ->
+                String.join("_", b.getCcmNo(), b.getShiftGroup(), b.getShift(), Optional.ofNullable(b.getLicensePlate()).orElse(""),
+                        DateFormatUtils.format(DateUtils.getStartOfDay(b.getCreateTime()), "yyyy-MM-dd"))
+        ));
+
+        // Step 4: 处理每条 bill
+        for (StorageBill bill : bills) {
+            String key = String.join("_", bill.getCcmNo(), bill.getShiftGroup(), bill.getShift(),
+                    DateFormatUtils.format(DateUtils.getStartOfDay(bill.getCreateTime()), "yyyy-MM-dd"));
+
+            BilletHotsendChangeShift shiftRecord = shiftMap.get(key);
+            if (shiftRecord == null) {
+                log.warn("未找到交班记录,跳过: {}", bill.getId());
+                continue;
+            }
+
+            Date shiftStart = shiftRecord.getCreateTime();
+            Date shiftEnd = Optional.ofNullable(shiftRecord.getChangeShiftTime()).orElse(DateUtils.addDays(DateUtils.getStartOfDay(bill.getCreateTime()), 1));
+
+            boolean needCalcCarNum = bill.getCarNum() == null || bill.getCarNum() == 0;
+            boolean needCalcCarAllNum = bill.getCarAllNum() == null || bill.getCarAllNum() == 0;
+            boolean updated = false;
+
+            // 查找对应车次列表
+            String carNumKey = String.join("_", bill.getCcmNo(), bill.getShiftGroup(), bill.getShift(),
+                    Optional.ofNullable(bill.getLicensePlate()).orElse(""), DateFormatUtils.format(DateUtils.getStartOfDay(bill.getCreateTime()), "yyyy-MM-dd"));
+            List<StorageBill> relatedBills = billGroupMap.getOrDefault(carNumKey, new ArrayList<>()).stream()
+                    .filter(b -> b.getCreateTime().compareTo(shiftStart) >= 0 && b.getCreateTime().compareTo(shiftEnd) < 0)
+                    .sorted(Comparator.comparing(StorageBill::getCreateTime))
+                    .collect(Collectors.toList());
+
+            if (needCalcCarNum) {
+                long index = relatedBills.stream()
+                        .filter(b -> !b.getId().equals(bill.getId()))
+                        .filter(b -> b.getCreateTime().before(bill.getCreateTime()))
+                        .count();
+                bill.setCarNum((int) index + 1);
+                updated = true;
+            }
+
+            if (needCalcCarAllNum) {
+                List<StorageBill> allSameShift = allRelatedBills.stream()
+                        .filter(b -> b.getCcmNo().equals(bill.getCcmNo())
+                                && b.getShiftGroup().equals(bill.getShiftGroup())
+                                && b.getShift().equals(bill.getShift())
+                                && b.getCreateTime().compareTo(shiftStart) >= 0
+                                && b.getCreateTime().compareTo(shiftEnd) < 0)
+                        .sorted(Comparator.comparing(StorageBill::getCreateTime))
+                        .collect(Collectors.toList());
+                long totalIndex = allSameShift.stream()
+                        .filter(b -> !b.getId().equals(bill.getId()))
+                        .filter(b -> b.getCreateTime().before(bill.getCreateTime()))
+                        .count();
+                bill.setCarAllNum((int) totalIndex + 1);
+                updated = true;
+            }
+
+            if (updated) this.updateById(bill);
+
+            // 更新交班 outCarNum
+            if (shiftRecord.getOutCarNum() == null || shiftRecord.getOutCarNum() == 0) {
+                shiftRecord.setOutCarNum(bill.getCarAllNum());
+                billetHotsendChangeShiftService.updateById(shiftRecord);
+            }
+        }
+    }
+
+
+    private Date getMinDate(List<StorageBill> bills) {
+        return bills.stream()
+                .map(StorageBill::getCreateTime)
+                .min(Date::compareTo)
+                .map(DateUtils::getStartOfDay)
+                .orElse(new Date());
+    }
+
+    private Date getMaxDate(List<StorageBill> bills) {
+        return bills.stream()
+                .map(StorageBill::getCreateTime)
+                .max(Date::compareTo)
+                .map(d -> DateUtils.addDays(DateUtils.getStartOfDay(d), 1))
+                .orElse(new Date());
+    }
+
 
     // 计算整数总和的方法
     private int calculateIntSum(List<DestinationStatisticsDetails> list) {