donglang 1 месяц назад
Родитель
Сommit
ba9f811ad9

+ 60 - 27
sckw-modules/sckw-transport/src/main/java/com/sckw/transport/handler/TakingOrderHandler.java

@@ -17,12 +17,13 @@ import com.sckw.order.api.model.UpdateActualAmountParam;
 import com.sckw.transport.model.*;
 import com.sckw.transport.model.param.OrderCirculateTakingQueryParam;
 import com.sckw.transport.model.param.OrderTakingResp;
-import com.sckw.transport.repository.KwtLogisticsOrderCirculateRepository;
 import lombok.extern.slf4j.Slf4j;
+import org.jetbrains.annotations.NotNull;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 
 import java.math.BigDecimal;
+import java.math.RoundingMode;
 import java.util.*;
 import java.util.function.Function;
 import java.util.stream.Collectors;
@@ -104,12 +105,12 @@ public class TakingOrderHandler extends AbstractWaybillOrderHandler<OrderCircula
         //4、生成车辆运单-装卸货信息
         createWaybillOrderTicket(param, logOrder, waybillOrder, waybillOrderSubtask, addresses, truck);
 
-        //5、更新上游订单:回写贸易订单
-        updateTradeOrder(tradeOrder, truckLoadVolume);
-
-        //6、更新上游订单:回写物流订单
+        //5、更新上游订单:回写物流订单
         updateLogOrder(logOrder, truckLoadVolume);
 
+        //6、更新上游订单:回写贸易订单
+//        updateTradeOrder(tradeOrder, truckLoadVolume);
+
         BusinessContext.set("createdWaybillOrder", waybillOrder);
 
         log.info("物流订单接单完成,运单ID:{}", waybillOrder.getId());
@@ -229,16 +230,8 @@ public class TakingOrderHandler extends AbstractWaybillOrderHandler<OrderCircula
             log.info("车辆无皮重,按80%核定载重计算,车辆任务量:{}", loadVolume);
         }
 
-        //订单分配总量
-        BigDecimal entrustAmount = tradeOrder.getAmount();
-        //订单实际交付量
-        BigDecimal actualAmount = tradeOrder.getActualAmount();
-        if (entrustAmount == null || actualAmount == null ||  BigDecimal.ZERO.compareTo(actualAmount) == 0) {
-            throw new BusinessPlatfromException(ErrorCodeEnum.PARAM_ERROR, "订单分配总量或订单实际交付量不能为空!");
-        }
-        //订单余量 = 分配总量 - 实际交付量
-        BigDecimal remainingAmount = entrustAmount.subtract(actualAmount);
-        log.info("订单余量 = 分配总量:{} - 实际交付量:{} = 车辆任务量:{}", entrustAmount, actualAmount, remainingAmount);
+        //订单余量
+        BigDecimal remainingAmount = getRemainingAmount(tradeOrder);
 
         // 最终接取的任务量
         BigDecimal taskAmount;
@@ -259,6 +252,53 @@ public class TakingOrderHandler extends AbstractWaybillOrderHandler<OrderCircula
         return taskAmount;
     }
 
+    @NotNull
+    private BigDecimal getRemainingAmount(OrderDetailVo tradeOrder) {
+        //订单分配总量
+        BigDecimal entrustAmount = tradeOrder.getAmount();
+        if (entrustAmount == null ||  entrustAmount.compareTo(BigDecimal.ZERO) <= 0) {
+            throw new BusinessPlatfromException(ErrorCodeEnum.PARAM_ERROR, "订单分配总量必须大于0!");
+        }
+        //物流订单
+        List<KwtLogisticsOrder> logisticsOrders = logisticsOrderRepository.queryByTradeOrderId(tradeOrder.getId());
+        if (CollectionUtils.isEmpty(logisticsOrders)) {
+            throw new BusinessPlatfromException(ErrorCodeEnum.LOGISTICS_ORDER_NOT_FOUND, "物流订单数据不存在!");
+        }
+
+        BigDecimal[] totals = logisticsOrders.stream()
+                .reduce(
+                        new BigDecimal[]{BigDecimal.ZERO, BigDecimal.ZERO, BigDecimal.ZERO}, // [totalLoad, totalEntrust, totalUnload]
+                        (acc, order) -> {
+                            // 累计已接单量
+                            acc[0] = acc[0].add(Optional.ofNullable(order.getEntrustAmount()).orElse(BigDecimal.ZERO));
+                            // 累计装货量
+                            acc[1] = acc[1].add(Optional.ofNullable(order.getTotalLoadAmount()).orElse(BigDecimal.ZERO));
+                            // 累计卸货量
+                            acc[2] = acc[2].add(Optional.ofNullable(order.getTotalUnloadAmount()).orElse(BigDecimal.ZERO));
+                            return acc;
+                        },
+                        (a, b) -> new BigDecimal[]{a[0].add(b[0]), a[1].add(b[1]), a[2].add(b[2])}
+                );
+        // 累计装货量/卸货量
+        BigDecimal totalLoadAmount = tradeOrder.getChargeType() == 1 ? totals[1] : totals[2];
+
+        // 已接单量
+        BigDecimal totalEntrustAmount = totals[0];
+
+        //订单余量 = 订单总量-所有物流订单(已接单量+累计装货量/累计卸货量)
+        BigDecimal remainingAmount = entrustAmount.subtract(totalEntrustAmount)
+                .subtract(totalLoadAmount)
+                .setScale(6, RoundingMode.HALF_UP);
+        log.info("订单余量 = 订单总量:{} - 累计装/卸货量:{} - 已接单量:{}", entrustAmount, totalLoadAmount, totalEntrustAmount);
+
+        // 校验余量是否为负
+        if (remainingAmount.compareTo(BigDecimal.ZERO) < 0) {
+            throw new BusinessPlatfromException(ErrorCodeEnum.PARAM_ERROR,
+                    "订单已分配总量(已接单量+累计装货/卸货量)超过订单总量!");
+        }
+        return remainingAmount;
+    }
+
     /**
      * 创建物流运单
      *
@@ -305,8 +345,6 @@ public class TakingOrderHandler extends AbstractWaybillOrderHandler<OrderCircula
         subtask.setUnit("吨"); //TODO DONGLANG
 
         subtask.setEntrustAmount(truckLoadVolume);
-        subtask.setLoadTime(waybillOrder.getTaskStartTime());
-        subtask.setUnloadTime(waybillOrder.getEndTime());
         subtask.setStatus(CarWaybillV1Enum.PENDING_VEHICLE.getCode());
         subtask.setCreateBy(param.getDriverId());
         subtask.setUpdateBy(param.getDriverId());
@@ -465,16 +503,11 @@ public class TakingOrderHandler extends AbstractWaybillOrderHandler<OrderCircula
     private void updateLogOrder(KwtLogisticsOrder logOrder, BigDecimal truckLoadVolume) {
         log.info("更新上游物流运输量数据,logOrderId:{}", logOrder);
         // 计算当前车辆总运输量
-        BigDecimal totalLoadVolume = Optional.ofNullable(logOrder.getEntrustAmount())
-                .map(entrust -> entrust.add(truckLoadVolume))
-                .orElse(truckLoadVolume);
-
-        Integer totalTake = Optional.ofNullable(logOrder.getTotalTake())
-                .map(val ->val + 1)
-                .orElse(0);
-
-        logOrder.setEntrustAmount(totalLoadVolume);
-        logOrder.setTotalTake(totalTake);
+        if (logOrder.getEntrustAmount() == null || BigDecimal.ZERO.compareTo(logOrder.getEntrustAmount()) == 0) {
+            logOrder.setEntrustAmount(truckLoadVolume);
+        } else {
+            logOrder.setEntrustAmount(logOrder.getEntrustAmount().add(truckLoadVolume));
+        }
         logisticsOrderRepository.updateById(logOrder);
         log.info("更新上游物流运输量成功, 物流订单ID:{}", logOrder.getId());
     }

+ 106 - 11
sckw-modules/sckw-transport/src/main/java/com/sckw/transport/handler/UnloadingHandler.java

@@ -3,16 +3,23 @@ package com.sckw.transport.handler;
 
 import com.sckw.core.common.enums.enums.ErrorCodeEnum;
 import com.sckw.core.exception.BusinessPlatfromException;
+import com.sckw.core.model.enums.AddressTypeEnum;
 import com.sckw.core.model.enums.CarWaybillV1Enum;
+import com.sckw.order.api.model.OrderDetailVo;
+import com.sckw.transport.model.KwtLogisticsOrder;
 import com.sckw.transport.model.KwtWaybillOrder;
 import com.sckw.transport.model.KwtWaybillOrderSubtask;
+import com.sckw.transport.model.KwtWaybillOrderTicket;
 import com.sckw.transport.model.param.WaybillOrderUnloadParam;
 import com.sckw.transport.repository.KwtWaybillOrderSubtaskRepository;
+import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
-import java.util.Date;
-import java.util.Objects;
+import java.math.BigDecimal;
+import java.util.*;
+import java.util.function.Function;
+import java.util.stream.Collectors;
 
 /**
  * Author: donglang
@@ -20,7 +27,7 @@ import java.util.Objects;
  * Des: 卸货
  * Version: 1.0
  */
-
+@Slf4j
 @Service
 public class UnloadingHandler extends AbstractWaybillOrderHandler<WaybillOrderUnloadParam>{
 
@@ -28,6 +35,10 @@ public class UnloadingHandler extends AbstractWaybillOrderHandler<WaybillOrderUn
     private KwtWaybillOrderSubtaskRepository waybillOrderSubtaskRepository;
 
 
+    //用于存储动态状态
+    private Integer targetStatus;
+
+
     @Override
     protected KwtWaybillOrder getWaybillOrder(WaybillOrderUnloadParam param) {
         return getWaybillOrder(param.getWaybillOrderId());
@@ -40,21 +51,104 @@ public class UnloadingHandler extends AbstractWaybillOrderHandler<WaybillOrderUn
             throw new BusinessPlatfromException(ErrorCodeEnum.WAYBILL_ORDER_NOT_FOUND, "运单不存在");
         }
         if (!Objects.equals(CarWaybillV1Enum.WAIT_LOADING.getCode(), waybill.getStatus())
-                || !Objects.equals(CarWaybillV1Enum.COMPLETION_UNLOADING.getCode(), waybill.getStatus())) {
+                && !Objects.equals(CarWaybillV1Enum.COMPLETION_UNLOADING.getCode(), waybill.getStatus())) {
             throw new BusinessPlatfromException(ErrorCodeEnum.WAYBILL_ORDER_STATUS_ERROR, "当前物流运单不是“已离场”或“审核驳回”状态,无法推进下一节点!");
         }
     }
 
     @Override
     protected void doBusiness(WaybillOrderUnloadParam param, KwtWaybillOrder waybill) {
-        //更新子运单卸货净重  TODO 审核通过后,贸易订单和物流订单的运输量需要已实际卸货净重为准
+        KwtLogisticsOrder logisticsOrder = logisticsOrderRepository.queryByLogisticsOrderId(waybill.getLOrderId());
+        if (logisticsOrder == null) {
+            throw new BusinessPlatfromException(ErrorCodeEnum.LOGISTICS_ORDER_NOT_FOUND, "物流订单数据不存在!");
+        }
+        OrderDetailVo orderDetailVo = tradeOrderInfoService.queryByTradeOrderId(logisticsOrder.getTOrderId());
+        if (orderDetailVo == null) {
+            throw new BusinessPlatfromException(ErrorCodeEnum.TRADE_ORDER_NOT_FOUND, "交易订单数据不存在!");
+        }
+
+        //按照装货量计算:推送到已完成状态
+        if (orderDetailVo.getChargeType() == 1) {
+            this.targetStatus = CarWaybillV1Enum.WAIT_UNLOADING.getCode();
+            //1.计算净装货量
+            BigDecimal loadAmount = getLoadAmount(param);
+
+            //2. 填充运单装货量
+            KwtWaybillOrderSubtask subtask = updateWaybillOrderSubtask(waybill, loadAmount);
+
+            //3. 更新物流订单
+            updateTradeOrder(logisticsOrder, loadAmount, subtask);
+
+        } else if (orderDetailVo.getChargeType() == 2) {
+            this.targetStatus = CarWaybillV1Enum.COMPLETION_LOADING.getCode();
+            //按照卸货量计算:推送到已卸货状态,更新子运单卸货净重
+            KwtWaybillOrderSubtask subtask = getWaybillSubtask(waybill.getId());
+            subtask.setUnloadAmount(param.getUnloadAmount());
+            subtask.setUnloadTime(new Date());
+            subtask.setUnloadUrl(param.getUnloadUrl());
+            subtask.setUnloadUploadTime(new Date());
+            subtask.setUnloadOperator(waybill.getDriverId());
+            waybillOrderSubtaskRepository.updateById(subtask);
+        }
+    }
+
+    /**
+     * 计算净装货量
+     * @param param
+     * @return
+     */
+    private BigDecimal getLoadAmount(WaybillOrderUnloadParam param) {
+        List<KwtWaybillOrderTicket> ticketList = waybillOrderTicketRepository.queryByWOrderId(param.getWaybillOrderId());
+        // 毛重
+        BigDecimal grossAmount = ticketList.stream().filter(Objects::nonNull)
+                .filter(ticket -> Objects.equals(ticket.getType(), AddressTypeEnum.TAKE.getCode()))
+                .findFirst()
+                .map(KwtWaybillOrderTicket::getGrossAmount)
+                .orElse(BigDecimal.ZERO);
+        // 皮重
+        BigDecimal tareAmount = ticketList.stream().filter(Objects::nonNull)
+                .filter(ticket -> Objects.equals(ticket.getType(), AddressTypeEnum.SHIPMENT.getCode()))
+                .findFirst()
+                .map(KwtWaybillOrderTicket::getTareAmount)
+                .orElse(BigDecimal.ZERO);
+        if (grossAmount.compareTo(BigDecimal.ZERO) <= 0 || tareAmount.compareTo(BigDecimal.ZERO) <= 0) {
+            throw new BusinessPlatfromException(ErrorCodeEnum.WAYBILL_ORDER_TICKET_NOT_FOUND, "运单车辆的皮重/毛重为空!");
+        }
+        //装货净重
+        return grossAmount.subtract(tareAmount);
+    }
+
+    /**
+     * 填充运单装货量
+     */
+    private KwtWaybillOrderSubtask updateWaybillOrderSubtask(KwtWaybillOrder waybill, BigDecimal loadAmount) {
         KwtWaybillOrderSubtask subtask = getWaybillSubtask(waybill.getId());
-        subtask.setUnloadAmount(param.getUnloadAmount());
-        subtask.setUnloadTime(new Date());
-        subtask.setUnloadUrl(param.getUnloadUrl());
-        subtask.setUnloadUploadTime(new Date());
-        subtask.setUnloadOperator(waybill.getDriverId());
+        subtask.setLoadAmount(loadAmount);
+        subtask.setLoadTime(new Date());
         waybillOrderSubtaskRepository.updateById(subtask);
+        return subtask;
+    }
+
+    /**
+     * 更新物流订单装货量和已委托量
+     */
+    private void updateTradeOrder(KwtLogisticsOrder logisticsOrder, BigDecimal loadAmount, KwtWaybillOrderSubtask subtask) {
+        //物流订单装货量累加
+        BigDecimal currentTotalLoad = Optional.ofNullable(logisticsOrder.getTotalLoadAmount())
+                .filter(amount -> amount.compareTo(BigDecimal.ZERO) > 0)
+                .orElse(BigDecimal.ZERO);
+        BigDecimal totalLoadAmount = currentTotalLoad.add(Optional.ofNullable(loadAmount).orElse(BigDecimal.ZERO));
+        logisticsOrder.setTotalLoadAmount(totalLoadAmount);
+
+        // 物流订单已委托量扣减
+        BigDecimal currentEntrust = Optional.ofNullable(logisticsOrder.getEntrustAmount())
+                .filter(amount -> amount.compareTo(BigDecimal.ZERO) > 0)
+                .orElse(BigDecimal.ZERO);
+        BigDecimal subtractAmount = Optional.ofNullable(subtask.getEntrustAmount()).orElse(BigDecimal.ZERO);
+        BigDecimal totalEntrustAmount = currentEntrust.subtract(subtractAmount);
+        // 确保已委托量不为负数
+        logisticsOrder.setEntrustAmount(totalEntrustAmount.compareTo(BigDecimal.ZERO) < 0 ? BigDecimal.ZERO : totalEntrustAmount);
+        logisticsOrderRepository.updateById(logisticsOrder);
     }
 
     @Override
@@ -64,7 +158,8 @@ public class UnloadingHandler extends AbstractWaybillOrderHandler<WaybillOrderUn
 
     @Override
     protected Integer getStatus() {
-        return CarWaybillV1Enum.COMPLETION_LOADING.getCode();
+        return Optional.ofNullable(this.targetStatus)
+                .orElse(CarWaybillV1Enum.COMPLETION_LOADING.getCode());
     }
 
     @Override

+ 1 - 1
sckw-modules/sckw-transport/src/main/java/com/sckw/transport/model/param/WaybillOrderUnloadParam.java

@@ -32,7 +32,7 @@ public class WaybillOrderUnloadParam extends WaybillOrderProcessParam implements
      * 卸货净重
      */
     @Schema(description = "卸货净重")
-    @NotBlank(message = "卸货净重不能为空!")
+    @NotNull(message = "卸货净重不能为空!")
     private BigDecimal unloadAmount;
 
     /**