fix(lastleg): complete stock transfer through linked relabel

This commit is contained in:
2026-10-04 20:21:16 +08:00
parent 7319fba35a
commit 76f02d8d45
17 changed files with 740 additions and 31 deletions
@@ -1080,6 +1080,57 @@ paths:
security: [{ bearerAuth: [] }]
parameters: [{ name: id, in: path, required: true, schema: { type: integer, format: int64 } }]
responses: { '200': { description: 当前客户海外尾程订单详情 }, '403': { description: 缺少海外尾程订单查看权限 }, '404': { description: 当前客户下订单不存在 } }
/api/platform/v1/last-leg/warehouse-transfers/{transferNo}/allocations:
post:
summary: 选择已有库存转运的真实来源
description: 权限lastleg:warehouse-transfer:manage;必须指定customerId。仅APPROVED原票选择精确来源位置和托盘,箱数等于原票箱数。needRelabel=true时按本票relabelBindings创建唯一关联换标并冻结所选数量,返回WAIT_RELABEL和relabelNo;客户完成作业复核确认后回到ALLOCATED,分配追随实际换标位置和新SKU。原idempotencyKey及原载荷重放不重复预留或建換标,同键异载荷冲突。
security: [{ bearerAuth: [] }]
parameters:
- { name: transferNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string } }
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [idempotencyKey, allocations]
properties:
idempotencyKey: { type: string, maxLength: 255 }
allocations:
type: array
minItems: 1
items:
type: object
required: [inventoryPositionId, palletId, packageCount]
properties:
inventoryPositionId: { type: integer, format: int64 }
palletId: { type: integer, format: int64 }
packageCount: { type: integer, minimum: 1 }
responses:
'200': { description: 原转运详情;allocations内skuCode为锁定的实际发货SKU,换标后返回新SKU;不包括已被换标替换的历史分配 }
'409': { description: 来源不可用或幂等载荷冲突 }
/api/platform/v1/last-leg/warehouse-transfers/{transferNo}/outbound:
post:
summary: 已有库存转运实际出库
description: 权限lastleg:warehouse-transfer:manage;必须指定customerId。仅ALLOCATED可执行,需换标本票必须关联本尾程订单的唯一换标申请,实际作业复核及客户确认已完成。按当前分配的新SKU和位置发货并保留唯一SHIP流水,不以MIXED聚合值替代实际SKU。成功原命令重放不重复扣减。
security: [{ bearerAuth: [] }]
parameters:
- { name: transferNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string } }
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [idempotencyKey]
properties:
idempotencyKey: { type: string, maxLength: 255 }
remark: { type: string, maxLength: 1000 }
responses:
'200': { description: 本票OUTBOUNDED事实或成功原命令重放 }
'409': { description: 尚未完成本票换标客户确认或分配不完整 }
/api/merchant/v1/last-leg/warehouse-transfers:
get:
summary: 客户分页查询自己的仓储转运单
@@ -2840,7 +2891,7 @@ components:
deliveryMethod: { type: string, nullable: true, enum: [TRUCK, PICKUP, EXPRESS] }
printShippingLabel: { type: boolean }
shippingLabelFileId: { type: string, nullable: true }
fulfillmentStatus: { type: string, nullable: true, enum: [WAIT_RELABEL, WAIT_PRE_DISPATCH, READY_FOR_OUTBOUND, OUTBOUND_CREATED, COMPLETED] }
fulfillmentStatus: { type: string, nullable: true, enum: [WAIT_RELABEL, WAIT_PRE_DISPATCH, WAIT_TRANSFER_OUTBOUND, READY_FOR_OUTBOUND, OUTBOUND_CREATED, OUTBOUNDED, COMPLETED] }
outboundOrderNo: { type: string, nullable: true }
customerConfirmedAt: { type: string, format: date-time, nullable: true }
reviewChannel: { type: string, enum: [TAIL_ORDER, RELABEL_ORDER], description: TAIL_ORDER 表示客户直接贴标,RELABEL_ORDER 表示其他业务关联换标 }