This commit is contained in:
2026-09-20 10:06:14 +08:00
parent d5c4059942
commit 507763a0d6
12 changed files with 199 additions and 24 deletions
@@ -117,6 +117,23 @@ class MeasurementRequestAuthenticatorTest {
verifyNoInteractions(guard);
}
@Test
@DisplayName("平台仓库设备允许tenantId为0并保留正数审计主体")
void shouldAcceptPlatformScopedWarehouseDevice() {
properties.setSignatureRequired(false);
MeasurementOpenApiProperties.AppCredential credential = properties.getApps().get("device-provider");
credential.setSecret(null);
credential.setTenantId(0L);
AuthenticatedMeasurementApp app = authenticator.authenticate("POST",
"/openapi/v1/inbound-measurements",
new MeasurementRequestHeaders("device-provider", null, null, null, null), "{}", false);
assertThat(app.tenantId()).isZero();
assertThat(app.subjectId()).isEqualTo(90001L);
assertThat(app.warehouseBindings()).containsEntry("CN-YW-01", 30001L);
}
@Test
@DisplayName("关闭签名仍强制上传请求携带幂等键")
void shouldStillRequireIdempotencyKeyWithoutSignature() {
@@ -48,6 +48,38 @@ class InboundCartonLabelServiceTest {
ReflectionTestUtils.setField(service, "internalToken", "internal-token");
}
@Test
void platformLookupUsesUniqueBoxCodeAndReturnsActualCustomerAndWarehouse() {
InboundCartonLabelEntity label = new InboundCartonLabelEntity();
label.setTenantId(10002L);
label.setInboundId(70002L);
label.setInboundDetailId(80002L);
label.setInboundCode("RK-002");
label.setBoxCode("RK-002#1-1");
label.setBatchStatus("ACTIVE");
label.setCartonIndex(1);
label.setTotalCartonCount(1);
InboundOrderEntity inbound = new InboundOrderEntity();
inbound.setWarehouseId(30001L);
when(repository.findGloballyByBoxCode("RK-002#1-1")).thenReturn(List.of(label));
when(repository.findInbound(10002L, 70002L)).thenReturn(inbound);
var resolved = service.resolvePlatformByBoxCode("RK-002#1-1");
assertThat(resolved.tenantId()).isEqualTo(10002L);
assertThat(resolved.warehouseId()).isEqualTo(30001L);
assertThat(resolved.binding().inboundId()).isEqualTo(70002L);
}
@Test
void platformLookupRejectsAmbiguousBoxCodeAcrossCustomers() {
when(repository.findGloballyByBoxCode("RK-002#1-1"))
.thenReturn(List.of(new InboundCartonLabelEntity(), new InboundCartonLabelEntity()));
assertThatThrownBy(() -> service.resolvePlatformByBoxCode("RK-002#1-1"))
.isInstanceOf(BizException.class).hasMessageContaining("归属不唯一");
}
@Test
void firstAllocationUsesCargoOrderAndFreezesEveryPhysicalCarton() {
InboundOrderEntity inbound = inbound();
@@ -55,12 +55,18 @@ class MojiaMeasurementOpenApiServiceTest {
CartonMeasurementService cartons = mock(CartonMeasurementService.class);
MeasurementImageClient images = mock(MeasurementImageClient.class);
MojiaMeasurementReceiptRepository receipts = mock(MojiaMeasurementReceiptRepository.class);
InboundCartonLabelService labels = mock(InboundCartonLabelService.class);
var service = new MojiaMeasurementOpenApiService(authenticator, cartons,
new ObjectMapper().findAndRegisterModules(), Validation.buildDefaultValidatorFactory().getValidator(),
images, receipts);
images, receipts, labels);
MeasurementRequestHeaders headers = new MeasurementRequestHeaders("mojia", null, null, null, null);
when(authenticator.authenticate("POST", MojiaMeasurementOpenApiService.CALLBACK_PATH,
headers, json(), false)).thenReturn(new AuthenticatedMeasurementApp("mojia", 10001L, 90001L, Map.of()));
headers, json(), false)).thenReturn(new AuthenticatedMeasurementApp(
"mojia", 0L, 90001L, Map.of("MJ-01", 30001L)));
when(labels.resolvePlatformByBoxCode("PCHK2608140001#5-1"))
.thenReturn(new InboundCartonLabelService.PlatformBinding(10001L, 30001L,
new CartonLabelBindingResolver.Binding(
70001L, 80001L, "PCHK2608140001", 1, 5, "60x40x30cm")));
when(cartons.upsert(eq(10001L), eq(90001L), any())).thenReturn(new CartonMeasurementResult(
1L, 1, 2L, "PCHK2608140001#5-1", "FBA19L5KMY2CU000002", 1,
new BigDecimal("60.1"), new BigDecimal("40.2"),
@@ -85,17 +91,19 @@ class MojiaMeasurementOpenApiServiceTest {
CartonMeasurementService cartons = mock(CartonMeasurementService.class);
MeasurementImageClient images = mock(MeasurementImageClient.class);
MojiaMeasurementReceiptRepository receipts = mock(MojiaMeasurementReceiptRepository.class);
InboundCartonLabelService labels = mock(InboundCartonLabelService.class);
var service = new MojiaMeasurementOpenApiService(authenticator, cartons,
new ObjectMapper().findAndRegisterModules(), Validation.buildDefaultValidatorFactory().getValidator(),
images, receipts);
images, receipts, labels);
ReflectionTestUtils.setField(service, "internalToken", "internal-token");
MeasurementRequestHeaders headers = new MeasurementRequestHeaders("mojia", null, null, null, null);
String requestJson = json().replace("\"shipment_id\":\"FBA19L5KMY2CU000002\",", "");
when(authenticator.authenticate("POST", MojiaMeasurementOpenApiService.CALLBACK_PATH,
headers, requestJson, false)).thenReturn(new AuthenticatedMeasurementApp("mojia", 10001L, 90001L, Map.of()));
when(cartons.upsert(eq(10001L), eq(90001L), any()))
headers, requestJson, false)).thenReturn(new AuthenticatedMeasurementApp(
"mojia", 0L, 90001L, Map.of("MJ-01", 30001L)));
when(labels.resolvePlatformByBoxCode("PCHK2608140001#5-1"))
.thenThrow(new BizException(ResultCode.NOT_FOUND, "箱号不存在或不属于当前客户"));
when(images.uploadReceipt(eq("internal-token"), eq(90001L), eq(10001L), any(Long.TYPE), any()))
when(images.uploadReceipt(eq("internal-token"), eq(90001L), eq(0L), any(Long.TYPE), any()))
.thenReturn(ApiResponse.success(new MeasurementImageClient.UploadResult(
3L, "mojia.jpg", "image/jpeg", 4L, "NOT_REQUIRED", null, null, null, null)));
@@ -113,6 +121,33 @@ class MojiaMeasurementOpenApiServiceTest {
assertThat(receipt.getValue().getLengthCm()).isEqualByComparingTo("60.1");
assertThat(receipt.getValue().getImageFileId()).isEqualTo(3L);
assertThat(receipt.getValue().getStatus()).isEqualTo("UNMATCHED");
assertThat(receipt.getValue().getTenantId()).isZero();
}
@Test
void platformMachineCannotWriteAnInboundFromAnotherWarehouse() {
MeasurementRequestAuthenticator authenticator = mock(MeasurementRequestAuthenticator.class);
CartonMeasurementService cartons = mock(CartonMeasurementService.class);
MeasurementImageClient images = mock(MeasurementImageClient.class);
MojiaMeasurementReceiptRepository receipts = mock(MojiaMeasurementReceiptRepository.class);
InboundCartonLabelService labels = mock(InboundCartonLabelService.class);
var service = new MojiaMeasurementOpenApiService(authenticator, cartons,
new ObjectMapper().findAndRegisterModules(), Validation.buildDefaultValidatorFactory().getValidator(),
images, receipts, labels);
MeasurementRequestHeaders headers = new MeasurementRequestHeaders("mojia", null, null, null, null);
when(authenticator.authenticate("POST", MojiaMeasurementOpenApiService.CALLBACK_PATH,
headers, json(), false)).thenReturn(new AuthenticatedMeasurementApp(
"mojia", 0L, 90001L, Map.of("MJ-01", 30001L)));
when(labels.resolvePlatformByBoxCode("PCHK2608140001#5-1"))
.thenReturn(new InboundCartonLabelService.PlatformBinding(10002L, 30002L,
new CartonLabelBindingResolver.Binding(
70002L, 80002L, "PCHK2608140001", 1, 5, "60x40x30cm")));
org.assertj.core.api.Assertions.assertThatThrownBy(() -> service.receive(headers, json()))
.isInstanceOf(BizException.class)
.hasMessageContaining("不属于当前设备绑定仓库");
verify(cartons, org.mockito.Mockito.never()).upsert(any(Long.TYPE), any(Long.TYPE), any());
}
private String json() {