贴标申请,仓储转运
This commit is contained in:
+20
@@ -1,6 +1,8 @@
|
||||
package com.baiyue.lastleg.palletops.controller;
|
||||
|
||||
import com.baiyue.lastleg.palletops.dto.PalletOperationResponses;
|
||||
import com.baiyue.lastleg.palletops.mapper.PdaPalletOperationMapper;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.apache.ibatis.annotations.Select;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
@@ -8,6 +10,7 @@ import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.List;
|
||||
import java.util.Arrays;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
@@ -35,4 +38,21 @@ class PdaPalletOperationControllerContractTest {
|
||||
assertFalse(sql.contains("<"));
|
||||
assertFalse(sql.contains(">"));
|
||||
}
|
||||
|
||||
@Test void relabelSourceAndResolvedPalletSerializeSnowflakeIdsAsStrings() throws Exception {
|
||||
ObjectMapper mapper = new ObjectMapper();
|
||||
var source = new PalletOperationResponses.RelabelSource(2100204001227157507L, 2L,
|
||||
2100203890682015746L, "PLT-1", "LOC-1", "IN-1", 1L, 1L, List.of("C-1"));
|
||||
var content = new PalletOperationResponses.PalletContent(2100203890682015746L, "PLT-1",
|
||||
"OCCUPIED", 1, 2092783373163335682L, "LOC-1", null, 1L, List.of());
|
||||
|
||||
assertEquals("2100204001227157507", mapper.readTree(mapper.writeValueAsString(source))
|
||||
.path("positionId").textValue());
|
||||
assertEquals("2100203890682015746", mapper.readTree(mapper.writeValueAsString(source))
|
||||
.path("palletId").textValue());
|
||||
assertEquals("2100203890682015746", mapper.readTree(mapper.writeValueAsString(content))
|
||||
.path("palletId").textValue());
|
||||
assertEquals("2092783373163335682", mapper.readTree(mapper.writeValueAsString(content))
|
||||
.path("locationId").textValue());
|
||||
}
|
||||
}
|
||||
|
||||
+20
@@ -9,6 +9,7 @@ import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.server.ResponseStatusException;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.test.web.client.match.MockRestRequestMatchers.requestTo;
|
||||
import static org.springframework.test.web.client.response.MockRestResponseCreators.withSuccess;
|
||||
|
||||
@@ -37,4 +38,23 @@ class HttpPalletPhysicalGatewayTest {
|
||||
.hasMessageContaining("404");
|
||||
server.verify();
|
||||
}
|
||||
|
||||
@Test
|
||||
void resolveIgnoresNewWarehousePalletMetadata() {
|
||||
server.expect(requestTo("http://warehouse/internal/v1/warehouse-pallets/resolve/PAL-1"))
|
||||
.andRespond(withSuccess("""
|
||||
{"code":"200","message":"success","data":{"palletId":"30","palletCode":"PAL-1",
|
||||
"warehouseId":"88","locationId":"40","status":"IDLE","fbaWarehouseCode":"XLX1",
|
||||
"unitPrice":1.00,"version":2,"locationType":"VIRTUAL","locationStatus":"ACTIVE",
|
||||
"reservable":true,"reservationBlockReason":null},
|
||||
"timestamp":"2026-09-19T03:18:35.283336500Z"}
|
||||
""", MediaType.APPLICATION_JSON));
|
||||
|
||||
var result = gateway.resolve("PAL-1");
|
||||
|
||||
assertThat(result.palletId()).isEqualTo(30L);
|
||||
assertThat(result.palletCode()).isEqualTo("PAL-1");
|
||||
assertThat(result.fbaWarehouseCode()).isEqualTo("XLX1");
|
||||
server.verify();
|
||||
}
|
||||
}
|
||||
|
||||
+65
-2
@@ -18,6 +18,11 @@ import com.baiyue.lastleg.relabel.entity.RelabelItem;
|
||||
import com.baiyue.lastleg.relabel.mapper.RelabelApplicationMapper;
|
||||
import com.baiyue.lastleg.relabel.mapper.RelabelItemMapper;
|
||||
import com.baiyue.lastleg.relabel.service.RelabelPalletMutationService;
|
||||
import com.baiyue.lastleg.returnreceipt.entity.ReturnInventoryCarton;
|
||||
import com.baiyue.lastleg.returnreceipt.entity.ReturnInventoryCartonItem;
|
||||
import com.baiyue.lastleg.returnreceipt.mapper.ReturnInventoryBalanceMapper;
|
||||
import com.baiyue.lastleg.returnreceipt.mapper.ReturnInventoryCartonMapper;
|
||||
import com.baiyue.lastleg.returnreceipt.mapper.ReturnInventoryCartonItemMapper;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
@@ -62,6 +67,9 @@ class PdaPalletOperationServiceTest {
|
||||
@Mock private RelabelApplicationMapper relabelApplications;
|
||||
@Mock private RelabelItemMapper relabelItems;
|
||||
@Mock private RelabelPalletMutationService relabelPalletMutations;
|
||||
@Mock private ReturnInventoryCartonMapper returnCartons;
|
||||
@Mock private ReturnInventoryCartonItemMapper returnCartonItems;
|
||||
@Mock private ReturnInventoryBalanceMapper returnBalances;
|
||||
private PdaPalletOperationService service;
|
||||
|
||||
@BeforeEach void setUp() {
|
||||
@@ -75,10 +83,44 @@ class PdaPalletOperationServiceTest {
|
||||
ReflectionTestUtils.setField(service, "relabelApplications", relabelApplications);
|
||||
ReflectionTestUtils.setField(service, "relabelItems", relabelItems);
|
||||
ReflectionTestUtils.setField(service, "relabelPalletMutations", relabelPalletMutations);
|
||||
ReflectionTestUtils.setField(service, "returnCartons", returnCartons);
|
||||
ReflectionTestUtils.setField(service, "returnCartonItems", returnCartonItems);
|
||||
ReflectionTestUtils.setField(service, "returnBalances", returnBalances);
|
||||
ReflectionTestUtils.setField(service, "objectMapper", new ObjectMapper().findAndRegisterModules());
|
||||
service.configureTransactions(new NoOpTransactionManager());
|
||||
}
|
||||
|
||||
@Test void partialReturnRelabelKeepsUnlabelledRemainderOnOriginalPallet() {
|
||||
RelabelApplication app = new RelabelApplication(); app.setId(600L); app.setCustomerId("100"); app.setRelabelNo("RL-1");
|
||||
RelabelItem item = new RelabelItem(); item.setId(701L); item.setSkuCode("SKU-1");
|
||||
item.setReturnCartonId(801L); item.setDestinationFbaWarehouseCode("XLX6");
|
||||
ReturnInventoryCarton original = new ReturnInventoryCarton(); original.setId(801L);
|
||||
original.setCustomerId("100"); original.setOverseasWarehouseId("88");
|
||||
original.setTotalQuantity(100L); original.setPalletCode("OLD");
|
||||
ReturnInventoryCartonItem originalLine = new ReturnInventoryCartonItem();
|
||||
originalLine.setId(901L); originalLine.setSkuCode("SKU-1"); originalLine.setQuantity(100L);
|
||||
when(relabelItems.selectList(any())).thenReturn(List.of(item));
|
||||
when(returnCartonItems.lockCarton(801L)).thenReturn(List.of(originalLine));
|
||||
when(returnCartonItems.updateById(any(ReturnInventoryCartonItem.class))).thenReturn(1);
|
||||
when(returnCartons.releasePartial(801L, "100", 600L, 70L)).thenReturn(1);
|
||||
when(returnCartons.insert(any(ReturnInventoryCarton.class))).thenReturn(1);
|
||||
when(returnCartonItems.insert(any(ReturnInventoryCartonItem.class))).thenReturn(1);
|
||||
when(returnBalances.adjustCartonQuantity("100", "88", "SKU-1", 1)).thenReturn(1);
|
||||
when(relabelItems.updateById(any(RelabelItem.class))).thenReturn(1);
|
||||
|
||||
ReflectionTestUtils.invokeMethod(service, "splitReturnRelabelCarton", app, item, original,
|
||||
pallet(30L, "NEW-XLX6", 88L, 0), 30L);
|
||||
|
||||
assertEquals(70L, originalLine.getQuantity());
|
||||
var moved = ArgumentCaptor.forClass(ReturnInventoryCarton.class);
|
||||
verify(returnCartons).insert(moved.capture());
|
||||
assertEquals(30L, moved.getValue().getTotalQuantity());
|
||||
assertEquals("NEW-XLX6", moved.getValue().getPalletCode());
|
||||
assertEquals("XLX6", moved.getValue().getDestinationWarehouseCode());
|
||||
assertEquals(moved.getValue().getId(), item.getReturnCartonId());
|
||||
verify(returnBalances).adjustCartonQuantity("100", "88", "SKU-1", 1);
|
||||
}
|
||||
|
||||
@Test void resolveRejectsPalletOutsideTokenFrozenWarehouse() {
|
||||
when(physical.resolve("P-1")).thenReturn(pallet(10L, "P-1", 99L, 1));
|
||||
assertThrows(ResponseStatusException.class, () -> service.resolve(identity(),
|
||||
@@ -100,7 +142,7 @@ class PdaPalletOperationServiceTest {
|
||||
RelabelApplication application = new RelabelApplication(); application.setRelabelNo("RL-1");
|
||||
application.setStatus("READY_FOR_OUTBOUND"); application.setOverseasWarehouseId("88");
|
||||
when(relabelApplications.findAnyByRelabelNo("RL-1")).thenReturn(application);
|
||||
when(physical.ensureRelabelPallet(88L, "RL-1:new-pallet-1")).thenReturn(
|
||||
when(physical.ensureRelabelPallet(88L, "RL-1:new-pallet-1", null)).thenReturn(
|
||||
new PalletPhysicalGateway.PalletReference(30L, "PAL-NEW-1", 88L, 1030L, "IDLE", null, 0));
|
||||
|
||||
var result = service.createRelabelPallet(identity(),
|
||||
@@ -358,6 +400,27 @@ class PdaPalletOperationServiceTest {
|
||||
assertEquals(java.util.Set.of(), ReflectionTestUtils.invokeMethod(service, "boundRelabelMarks", app));
|
||||
}
|
||||
|
||||
@Test void relabelSourcesExposeAuthoritativePalletId() {
|
||||
var tasks = mock(com.baiyue.lastleg.relabel.pda.mapper.PdaRelabelTaskMapper.class);
|
||||
ReflectionTestUtils.setField(service, "relabelWorkTasks", tasks);
|
||||
RelabelApplication app = new RelabelApplication(); app.setId(600L); app.setCustomerId("100");
|
||||
app.setRelabelNo("RL-1"); app.setOverseasWarehouseId("88"); app.setStatus("READY_FOR_OUTBOUND");
|
||||
app.setFulfillmentStatus("WAIT_PRE_DISPATCH");
|
||||
when(relabelApplications.findAnyByRelabelNo("RL-1")).thenReturn(app);
|
||||
RelabelItem item = relabelItem(701L, "CARTON-A", 100L);
|
||||
when(relabelItems.selectList(any())).thenReturn(List.of(item));
|
||||
when(positions.selectById(100L)).thenReturn(position(100L, 20L, "DISPLAY-CODE", 1L, 3L));
|
||||
PalletInventoryRow source = row(100L, 20L, 3L, 0L); source.setPalletNo("CANONICAL-CODE");
|
||||
source.setHoldPackages(1L);
|
||||
when(mapper.relabelSources("100", "88", 200L)).thenReturn(List.of(source));
|
||||
|
||||
var result = service.relabelSources(identity(), new PalletOperationRequests.RelabelSources("RL-1"));
|
||||
|
||||
assertEquals(1, result.size());
|
||||
assertEquals(20L, result.get(0).palletId());
|
||||
assertEquals("CANONICAL-CODE", result.get(0).palletCode());
|
||||
}
|
||||
|
||||
@Test void createsPalletBeforeCustomerConfirmationOnlyForClaimingOperator() {
|
||||
var tasks = mock(com.baiyue.lastleg.relabel.pda.mapper.PdaRelabelTaskMapper.class);
|
||||
ReflectionTestUtils.setField(service, "relabelWorkTasks", tasks);
|
||||
@@ -366,7 +429,7 @@ class PdaPalletOperationServiceTest {
|
||||
when(relabelApplications.findAnyByRelabelNo("RL-1")).thenReturn(app);
|
||||
var task = new com.baiyue.lastleg.relabel.pda.entity.PdaRelabelTask(); task.setStatus("PROCESSING"); task.setOperatorKey("7");
|
||||
when(tasks.find("100", 600L)).thenReturn(task);
|
||||
when(physical.ensureRelabelPallet(88L, "RL-1:before-confirm")).thenReturn(pallet(30L, "NEW", 88L, 0));
|
||||
when(physical.ensureRelabelPallet(88L, "RL-1:before-confirm", null)).thenReturn(pallet(30L, "NEW", 88L, 0));
|
||||
assertEquals("NEW", service.createRelabelPallet(identity(), new PalletOperationRequests.NewRelabelPallet("RL-1", "before-confirm")).palletCode());
|
||||
task.setOperatorKey("other");
|
||||
assertThrows(ResponseStatusException.class, () -> service.createRelabelPallet(identity(), new PalletOperationRequests.NewRelabelPallet("RL-1", "different")));
|
||||
|
||||
Reference in New Issue
Block a user