fix: 按物理箱贯通一件代发履约箱数
This commit is contained in:
+5
-1
@@ -13,6 +13,10 @@ class LoadingModelBridgeMapperContractTest {
|
||||
.getMethod("allocatedPackages", long.class, long.class, long.class)
|
||||
.getAnnotation(Select.class).value()).replaceAll("\\s+", " ");
|
||||
|
||||
assertThat(sql).contains("inbound_id=#{inboundId} AND deleted=0");
|
||||
assertThat(sql)
|
||||
.contains("item.inbound_id=#{inboundId} AND item.deleted=0")
|
||||
.contains("COUNT(DISTINCT carton.id)")
|
||||
.contains("pallet_item.pallet_id=carton.pallet_id")
|
||||
.contains("pallet_item.deleted=0");
|
||||
}
|
||||
}
|
||||
|
||||
+29
@@ -300,6 +300,8 @@ class LoadingCompletedOutboxServiceTest {
|
||||
assertThat(actualPalletsSql)
|
||||
.contains("pallet.pallet_no AS pallet_code")
|
||||
.contains("item.pallet_id=pallet.id")
|
||||
.contains("LEFT JOIN fl_dropship_pallet_carton_sku carton_sku")
|
||||
.contains("COALESCE(carton_sku.inbound_detail_id,carton.inbound_detail_id)")
|
||||
.doesNotContain("pallet.pallet_code");
|
||||
assertThat(workPalletCountSql).contains("i.pallet_id=p.id");
|
||||
assertThat(openWorkPalletCountSql).contains("i.pallet_id=p.id");
|
||||
@@ -374,6 +376,33 @@ class LoadingCompletedOutboxServiceTest {
|
||||
assertThat(event.payload().at("/orders/0/palletCount").asInt()).isEqualTo(2);
|
||||
}
|
||||
|
||||
@Test
|
||||
void multiSkuCartonsKeepSkuSnapshotsButCountPhysicalPackagesOnce() throws Exception {
|
||||
Row first = row(11, 100, 101); first.setFulfillmentType("ONE_CLICK_DROPSHIP");
|
||||
first.setPackageCount(2); first.setProductQuantity(20); first.setSkuCode("SKU-A");
|
||||
Row second = row(11, 100, 102); second.setFulfillmentType("ONE_CLICK_DROPSHIP");
|
||||
second.setPackageCount(2); second.setProductQuantity(10); second.setSkuCode("SKU-B");
|
||||
when(snapshots.rows(90L)).thenReturn(List.of(first, second));
|
||||
when(snapshots.workPalletCount(90L)).thenReturn(1);
|
||||
when(snapshots.actualPalletRows(90L)).thenReturn(List.of(
|
||||
actualPallet(11,100,"DP-260916-0009",101,"SKU-A","BOX-001",10),
|
||||
actualPallet(11,100,"DP-260916-0009",102,"SKU-B","BOX-001",5),
|
||||
actualPallet(11,100,"DP-260916-0009",101,"SKU-A","BOX-002",10),
|
||||
actualPallet(11,100,"DP-260916-0009",102,"SKU-B","BOX-002",5)));
|
||||
|
||||
service.publish(90L);
|
||||
|
||||
ArgumentCaptor<InboundOutboxEntity> captor = ArgumentCaptor.forClass(InboundOutboxEntity.class);
|
||||
verify(outbox).insert(captor.capture());
|
||||
EventEnvelope event = mapper.readValue(captor.getValue().getPayloadJson(), EventEnvelope.class);
|
||||
assertThat(event.payload().at("/orders/0/packageCount").asInt()).isEqualTo(2);
|
||||
assertThat(event.payload().at("/orders/0/items")).hasSize(2);
|
||||
assertThat(event.payload().at("/orders/0/pallets/0/manifestPackageCount").asInt()).isEqualTo(2);
|
||||
assertThat(event.payload().at("/orders/0/pallets/0/skuPackages")).hasSize(2);
|
||||
assertThat(event.payload().at("/orders/0/pallets/0/skuPackages/0/cartonMarks")).hasSize(2);
|
||||
assertThat(event.payload().at("/orders/0/pallets/0/skuPackages/1/cartonMarks")).hasSize(2);
|
||||
}
|
||||
|
||||
@Test void publishesExactPdaCartonToPalletBindingsWithoutSequentialRedistribution() throws Exception {
|
||||
Row first = row(11, 100, 101); first.setFulfillmentType("ONE_CLICK_DROPSHIP");
|
||||
first.setPackageCount(2); first.setProductQuantity(20); first.setSkuCode("SKU-A");
|
||||
|
||||
@@ -155,6 +155,9 @@ class LoadingPickServiceTest {
|
||||
new LoadingPickItemMapper.InboundOwner(101L, 50L)));
|
||||
when(repository.inbound(anyLong(), anyLong())).thenAnswer(invocation ->
|
||||
new LoadingInboundMapper.Snapshot(invocation.getArgument(1), invocation.getArgument(0), "LOADING", 1));
|
||||
when(dropshipPallets.physicalMetricsByPalletIds(any())).thenReturn(List.of(
|
||||
new DropshipPalletizationMapper.PalletMetrics(801L, 2,
|
||||
java.math.BigDecimal.ZERO, java.math.BigDecimal.ZERO, java.math.BigDecimal.ZERO)));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -482,6 +485,39 @@ class LoadingPickServiceTest {
|
||||
verify(completionCommands, never()).latest(20L);
|
||||
}
|
||||
|
||||
@Test
|
||||
void taskDetailCollapsesMultiSkuRowsIntoOnePhysicalPalletCard() {
|
||||
LoadingPickItemEntity first = item();
|
||||
LoadingPickItemEntity second = item();
|
||||
second.setId(31L);
|
||||
second.setLoadingPlanItemId(41L);
|
||||
second.setInboundDetailId(61L);
|
||||
for (LoadingPickItemEntity item : List.of(first, second)) {
|
||||
item.setPlannedPackageCount(11);
|
||||
item.setUnitType("SEALED_PALLET");
|
||||
item.setPalletId(801L);
|
||||
item.setPalletNo("DP-260916-0009");
|
||||
item.setIndivisible(true);
|
||||
}
|
||||
when(dropshipPallets.physicalMetricsByPalletIds(any())).thenReturn(List.of(
|
||||
new DropshipPalletizationMapper.PalletMetrics(801L, 11,
|
||||
java.math.BigDecimal.ZERO, java.math.BigDecimal.ZERO, java.math.BigDecimal.ZERO)));
|
||||
when(repository.task(20L)).thenReturn(task());
|
||||
when(repository.items(20L, 101L)).thenReturn(List.of(first, second));
|
||||
when(repository.cartonLabels(20L)).thenReturn(List.of());
|
||||
when(repository.inboundOwners(20L)).thenReturn(List.of(
|
||||
new LoadingPickItemMapper.InboundOwner(101L, 50L)));
|
||||
when(palletAllocations.list(101L, 50L)).thenReturn(List.of(allocation(50L, 20)));
|
||||
|
||||
Task result = service.task(20L, 101L);
|
||||
|
||||
assertThat(result.items()).singleElement().satisfies(item -> {
|
||||
assertThat(item.palletNo()).isEqualTo("DP-260916-0009");
|
||||
assertThat(item.plannedPackageCount()).isEqualTo(11);
|
||||
assertThat(item.pickedPackageCount()).isZero();
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void loadingTaskDetailDoesNotDependOnCompletionCommandStorage() {
|
||||
LoadingPickTaskEntity task = task();
|
||||
|
||||
+40
-5
@@ -9,6 +9,7 @@ import com.baiyue.firstleg.entity.LoadingPickTaskEntity;
|
||||
import com.baiyue.firstleg.mapper.InboundSplitSettlementMapper;
|
||||
import com.baiyue.firstleg.mapper.InboundSplitSettlementMapper.MeasurementItemRow;
|
||||
import com.baiyue.firstleg.mapper.InboundSplitSettlementMapper.ParentRow;
|
||||
import com.baiyue.firstleg.mapper.DropshipPalletizationMapper;
|
||||
import com.baiyue.firstleg.repository.InboundPalletAllocationRepository;
|
||||
import com.baiyue.firstleg.repository.LoadingPickRepository;
|
||||
import jakarta.annotation.Resource;
|
||||
@@ -44,6 +45,7 @@ class PdaPickSettlementServiceTest {
|
||||
@MockBean private WarehousePalletLocationClient warehouse;
|
||||
@MockBean private OrderFulfillmentSplitClient orderSplits;
|
||||
@MockBean private InboundHoldGuard inboundHoldGuard;
|
||||
@MockBean private DropshipPalletizationMapper dropshipPallets;
|
||||
@Resource private PdaPickSettlementService service;
|
||||
|
||||
@Test
|
||||
@@ -205,7 +207,7 @@ class PdaPickSettlementServiceTest {
|
||||
}
|
||||
|
||||
@Test
|
||||
void settlesWholeDropshipPalletWithSkuFactsInsteadOfAggregateMeasurementDetail() {
|
||||
void settlesWholeDropshipUsingUnifiedPhysicalCartonMeasurement() {
|
||||
List<LoadingPickItemEntity> items = List.of(
|
||||
item(11L, 21L, 31L, 41L, 1, 1, "PICKED"),
|
||||
item(12L, 22L, 31L, 42L, 1, 1, "PICKED"),
|
||||
@@ -223,14 +225,47 @@ class PdaPickSettlementServiceTest {
|
||||
service.settle(1L, 9L, "operator");
|
||||
|
||||
verify(orderSplits).split(eq("internal-token"), eq(9L),
|
||||
org.mockito.ArgumentMatchers.argThat(request -> request.lines().size() == 4
|
||||
&& request.lines().stream().allMatch(line -> line.packageCount() == 1)
|
||||
&& request.lines().stream().map(OrderFulfillmentSplitClient.QuantityLine::sourceDetailId)
|
||||
.collect(java.util.stream.Collectors.toSet()).equals(java.util.Set.of(41L, 42L, 43L, 44L))));
|
||||
org.mockito.ArgumentMatchers.argThat(request -> request.lines().size() == 1
|
||||
&& request.lines().get(0).sourceDetailId() == 41L
|
||||
&& request.lines().get(0).packageCount() == 4));
|
||||
verify(splits).updateMeasurementItemForLoaded(10001L, 51L, 4);
|
||||
verify(splits).markSourceLoaded(10001L, 31L, 4, 9L, 3);
|
||||
}
|
||||
|
||||
@Test
|
||||
void multiSkuCartonsCountOnceWhenSettlingWholeDropshipPallet() {
|
||||
LoadingPickItemEntity first = item(11L, 21L, 31L, 41L, 20, 20, "PICKED");
|
||||
LoadingPickItemEntity second = item(12L, 22L, 31L, 42L, 20, 20, "PICKED");
|
||||
for (LoadingPickItemEntity item : List.of(first, second)) {
|
||||
item.setUnitType("SEALED_PALLET");
|
||||
item.setPalletId(801L);
|
||||
item.setPalletNo("DP-260916-0009");
|
||||
item.setIndivisible(true);
|
||||
}
|
||||
resolved(List.of(first, second));
|
||||
DropshipPalletizationMapper.PlanPalletMemberRow physical =
|
||||
new DropshipPalletizationMapper.PlanPalletMemberRow();
|
||||
physical.setPalletId(801L);
|
||||
physical.setAccountId(10001L);
|
||||
physical.setInboundId(31L);
|
||||
physical.setAvailablePackageCount(20);
|
||||
when(dropshipPallets.palletInboundMembersByPalletIds(any())).thenReturn(List.of(physical));
|
||||
when(splits.lockParent(31L)).thenReturn(parent(20));
|
||||
when(splits.fulfillmentType(10001L, 31L)).thenReturn("ONE_CLICK_DROPSHIP");
|
||||
when(splits.lockLatestApprovedItemsForInbound(10001L, 31L))
|
||||
.thenReturn(List.of(new MeasurementItemRow(51L, 61L, 41L, 20)));
|
||||
when(allocations.lockConfirmed(10001L, 31L))
|
||||
.thenReturn(List.of(allocation(1L, 1, 501L, 20)));
|
||||
writes(0, 20);
|
||||
|
||||
service.settle(1L, 9L, "operator");
|
||||
|
||||
verify(splits).markSourceLoaded(10001L, 31L, 20, 9L, 3);
|
||||
verify(orderSplits).split(eq("internal-token"), eq(9L),
|
||||
org.mockito.ArgumentMatchers.argThat(request -> request.loadedPackageCount() == 20
|
||||
&& request.lines().size() == 1 && request.lines().get(0).packageCount() == 20));
|
||||
}
|
||||
|
||||
@Test
|
||||
void onlyPureSkippedInboundRestoresCandidate() {
|
||||
LoadingPickItemEntity item = item(12L, 22L, 32L, 42L, 8, 0, "SKIPPED");
|
||||
|
||||
Reference in New Issue
Block a user