fix: enforce dropship pallet count for inbound plans

This commit is contained in:
2026-09-14 16:38:50 +08:00
parent 99f2c730e0
commit 26c37deb55
5 changed files with 82 additions and 5 deletions
@@ -120,6 +120,25 @@ class ContainerInboundPlanPreviewTest {
assertEquals("RESOURCE_PENDING", result.groups().get(0).orders().get(0).readiness());
}
@Test
void blocksExistingDropshipPlanWhosePalletCountDiffersFromFrozenSourcePallets() {
when(orderMapper.containerPreviewOrders("BOOKING-DROPSHIP-MISMATCH")).thenReturn(List.of(
row(1L, "LM-DROPSHIP", "ONE_CLICK_DROPSHIP", "OVERSEAS", "US-LAX-01", "洛杉矶仓", 2,
"IP-DROPSHIP", 2, 1, "PENDING_ASSIGNMENT", 0)
));
when(dropshipOrders.palletSnapshots("100", 1L)).thenReturn(List.of(
new DropshipPalletSnapshot("DP-260914-0001", 10, List.of())));
var result = service.previewContainer("BOOKING-DROPSHIP-MISMATCH");
var order = result.groups().get(0).orders().get(0);
assertFalse(result.ready());
assertEquals("BLOCKED", order.readiness());
assertEquals(List.of("DROPSHIP_PALLET_COUNT_MISMATCH"), order.blockers());
assertEquals(1, order.sourcePalletCount());
assertEquals(2, order.targetPalletCount());
}
@Test
void exposesHeadLegExistingSupplementAndFinalPalletCountsWithoutBlocking() {
when(orderMapper.containerPreviewOrders("BOOKING-SUPPLEMENT")).thenReturn(List.of(
@@ -183,6 +183,43 @@ class InboundPlanServiceTest {
verify(commandMapper, never()).insert(any(com.baiyue.lastleg.entity.LastlegOrderCommandRecord.class));
}
@Test
void oneClickDropshipManualPlanMustKeepTheFrozenSourcePalletCount() {
SourceOrderSnapshot source = order(2L, "RK-2", "3.3650", "WH-A");
when(orderMapper.lockOrder("100", 2L)).thenReturn(List.of(source));
when(orderMapper.findOrderType("100", 2L)).thenReturn("ONE_CLICK_DROPSHIP");
when(dropshipOrders.palletSnapshots("100", 2L)).thenReturn(List.of(
new DropshipPalletSnapshot("DP-260914-0001", 10L, List.of())));
ResponseStatusException error = assertThrows(ResponseStatusException.class, () -> service.convertManual(
new ManualInboundPlanRequest("100", 2L, 0, LocalDate.of(2026, 9, 15),
2, "WOOD", false, false, false, null), "dropship-pallet-mismatch", "900"));
assertEquals(400, error.getStatusCode().value());
assertEquals("一件代发人工计划托数必须与头程封托托盘数一致:1", error.getReason());
verify(planMapper, never()).insert(any(InboundPlan.class));
verify(commandMapper, never()).insert(any(com.baiyue.lastleg.entity.LastlegOrderCommandRecord.class));
}
@Test
void oneClickDropshipUsesFrozenSourcePalletCountInsteadOfVolumeSuggestion() {
SourceOrderSnapshot source = order(2L, "RK-2", "3.3650", "WH-A");
when(orderMapper.lockOrder("100", 2L)).thenReturn(List.of(source));
when(orderMapper.findOrderType("100", 2L)).thenReturn("ONE_CLICK_DROPSHIP");
when(dropshipOrders.palletSnapshots("100", 2L)).thenReturn(List.of(
new DropshipPalletSnapshot("DP-260914-0001", 10L, List.of())));
when(orderMapper.markPlannedManual(eq("100"), eq(2L), any(), eq(1), eq(false), eq(0), any()))
.thenReturn(1);
var result = service.convertManual(new ManualInboundPlanRequest("100", 2L, 0,
LocalDate.of(2026, 9, 15), 1, "WOOD", false, false, false, null),
"dropship-exact-pallet-count", "900");
assertEquals(1, result.palletCount());
verify(planMapper).insert(any(InboundPlan.class));
verify(palletMapper).insert(any(InboundPlanPallet.class));
}
@Test
void containerConversionBindsRealWarehousePalletsBackToSignedManualPlanBeforeReceiving() {
InboundPlan plan = existingPlan("100", 2L, "IP-MANUAL");