fix(oms):出库业务单线路/车次同步运输业务单,补齐触发入口与拆单时序

出库业务单与运输业务单为两张独立表,仅靠发票号经配送明细关联,
此前无字段同步逻辑,出库单填写的线路/车次不会流到运输业务单。

1. ReservationStockOutOrderDomainService新增syncLineInfoToBusinessOrder:
   按关联链 出库单号->reservation_delivery_details_link.invoiceNumber
   ->business_delivery_details_link.invoiceNumber 定位关联业务单,
   以出库业务单为源头覆盖lineCode/lineName/shuttleNo。
2. 触发入口三个:审核通过(auditState)/下发(issueOrder)/执行并下发
   (executeAndIssue);取消下发不触发。下发与执行并下发不经过审核
   动作,只挂审核入口会漏同步。
3. 同步目标同时覆盖orderId(未拆单业务单/拆单后主单)与subOrderId
   (拆单子单):仅同步subOrderId时,出库先审核而运输单尚未拆单
   (subOrderId为空)会落空,且主单无值导致后续拆单子单拷贝不到。
4. 同步失败仅记error日志,不阻断审核/下发主流程
   (状态更新与同步非同一事务,关联数据异常不应导致接口报错)。

边界:运输业务单手工创建且未录配送明细时无关联链不同步,需页面自行
填写;关联依赖发票号两侧一致,与既有退货回写为同一关联假设。
This commit is contained in:
rcx
2026-08-22 18:38:39 +08:00
parent 9068fa0e40
commit bb3dfaed4a
@@ -409,7 +409,7 @@ public class ReservationStockOutOrderDomainService {
String userRealName = loginUser.getUserPo() != null && loginUser.getUserPo().getUserName() != null
? loginUser.getUserPo().getUserName()
: (loginUser.getRealname() != null ? loginUser.getRealname() : loginUser.getUsername());
return stockOutOrderService.update(null, new UpdateWrapper<ReservationStockOutOrder>().lambda()
boolean updateResult = stockOutOrderService.update(null, new UpdateWrapper<ReservationStockOutOrder>().lambda()
.set(ReservationStockOutOrder::getReservationAuditId, loginUser.getUserid())
.set(ReservationStockOutOrder::getReservationAuditName, userRealName)
.set(ReservationStockOutOrder::getReservationAuditTime, new Date())
@@ -418,6 +418,67 @@ public class ReservationStockOutOrderDomainService {
.set(ReservationStockOutOrder::getUpdateTime, new Date())
.set(ReservationStockOutOrder::getIssueStatus, issueStatus)
.in(ReservationStockOutOrder::getOutOrderId, stockOutOrderDO.getOutOrderIds()));
//审核通过时同步线路/车次到关联的运输业务单
if (issueStatus == 2) {
syncLineInfoToBusinessOrder(stockOutOrderDO.getOutOrderIds());
}
return updateResult;
}
/**
* 将出库业务单的线路/车次同步到关联的运输业务单(审核通过/下发/执行并下发时触发):
* 关联链路 出库单号->reservation_delivery_details_link.invoiceNumber
* ->business_delivery_details_link.invoiceNumber->orderId(主单/未拆单)/subOrderId(拆单子单)
* 出库业务单与运输业务单为两张独立表,此前无字段同步逻辑,线路车次以出库业务单为源头覆盖;
* 同步失败仅记日志,不阻断主流程。
*/
private void syncLineInfoToBusinessOrder(List<Long> outOrderIds) {
try {
for (Long outOrderId : outOrderIds) {
ReservationStockOutOrder byId = stockOutOrderService.getById(outOrderId);
if (byId == null || StringUtils.isBlank(byId.getLineCode())) {
continue;
}
List<ReservationDeliveryDetailsLink> deliveryLinks = reservationDeliveryDetailsLinkService.list(
new LambdaQueryWrapper<ReservationDeliveryDetailsLink>()
.eq(ReservationDeliveryDetailsLink::getOrderNumber, byId.getOutOrderNumber()));
Set<String> syncedBusinessOrderIds = new HashSet<>();
for (ReservationDeliveryDetailsLink deliveryLink : deliveryLinks) {
if (StringUtils.isBlank(deliveryLink.getInvoiceNumber())) {
continue;
}
List<BusinessDeliveryDetailsLink> businessLinks = businessDeliveryDetailsLinkService.list(
new LambdaQueryWrapper<BusinessDeliveryDetailsLink>()
.eq(BusinessDeliveryDetailsLink::getInvoiceNumber, deliveryLink.getInvoiceNumber()));
//未拆单时orderId即运输业务单本身;拆单后orderId为主单、subOrderId为子单,两者均同步
//(若只同步subOrderId,出库业务单先于运输业务单拆单时subOrderId为空,同步落空,
// 且主单无值导致后续拆单子单也拷贝不到)
for (BusinessDeliveryDetailsLink businessLink : businessLinks) {
for (Object bizOrderIdObj : new Object[]{businessLink.getOrderId(), businessLink.getSubOrderId()}) {
if (bizOrderIdObj == null) {
continue;
}
String bizOrderId = String.valueOf(bizOrderIdObj);
if (!syncedBusinessOrderIds.add(bizOrderId)) {
continue;
}
BusinessDocumentOrder businessOrder = businessDocumentOrderMapper.selectOne(
new LambdaQueryWrapper<BusinessDocumentOrder>()
.eq(BusinessDocumentOrder::getId, bizOrderId));
if (businessOrder != null) {
businessOrder.setLineCode(byId.getLineCode());
businessOrder.setLineName(byId.getLineName());
businessOrder.setShuttleNo(byId.getShuttleNo());
businessDocumentOrderMapper.updateById(businessOrder);
}
}
}
}
}
} catch (Exception e) {
log.error("同步线路/车次到运输业务单失败, outOrderIds={}, error={}", outOrderIds, e.getMessage(), e);
}
}
/**
@@ -444,6 +505,9 @@ public class ReservationStockOutOrderDomainService {
.set(ReservationStockOutOrder::getUpdateTime, new Date())
.in(ReservationStockOutOrder::getOutOrderId, stockOutOrderDO.getOutOrderIds()));
//下发时同步线路/车次到关联的运输业务单(与审核通过触发同一同步,覆盖式)
syncLineInfoToBusinessOrder(stockOutOrderDO.getOutOrderIds());
//todo下发推送到wms
List<Long> inOrderIds = stockOutOrderDO.getOutOrderIds();
@@ -608,6 +672,9 @@ public class ReservationStockOutOrderDomainService {
.set(ReservationStockOutOrder::getUpdateTime, new Date())
.in(ReservationStockOutOrder::getOutOrderId, stockOutOrderDO.getOutOrderIds()));
//下发时同步线路/车次到关联的运输业务单(与审核通过触发同一同步,覆盖式)
syncLineInfoToBusinessOrder(stockOutOrderDO.getOutOrderIds());
//todo下发推送到wms
List<Long> inOrderIds = stockOutOrderDO.getOutOrderIds();