This commit is contained in:
2026-08-20 18:02:38 +08:00
parent b55b049e77
commit 1cd8b6a473
210 changed files with 6974 additions and 825 deletions
@@ -0,0 +1,312 @@
openapi: 3.0.3
info:
title: Lastleg Overseas Business API
version: 1.0.0
paths:
/api/platform/v1/last-leg/overseas-procurements:
get:
summary: 分页查询海外采购订单
description: 权限 platform:overseas-business:purchase:list;customerId 为空时查询全部客户。
security: [{ bearerAuth: [] }]
parameters:
- { name: customerId, in: query, schema: { type: string } }
- { name: page, in: query, required: true, schema: { type: integer, minimum: 1 } }
- { name: size, in: query, required: true, schema: { type: integer, minimum: 1, maximum: 200 } }
- { name: orderNo, in: query, schema: { type: string } }
- { name: customerKeyword, in: query, schema: { type: string } }
- { name: purchaseCategory, in: query, schema: { type: string } }
- { name: productName, in: query, schema: { type: string } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/ProcurementStatus' } }
- { name: purchaseWarehouseId, in: query, schema: { type: string } }
responses: { '200': { description: 统一 ApiResponse 包装的采购订单分页 } }
/api/platform/v1/last-leg/overseas-procurements/customer-options:
get:
summary: 查询已有采购订单的客户候选
description: 权限 platform:overseas-business:purchase:list;候选来自尾程库采购订单客户快照,不跨库查询 IAM。
security: [{ bearerAuth: [] }]
parameters:
- { name: keyword, in: query, schema: { type: string } }
- { name: limit, in: query, schema: { type: integer, minimum: 1, maximum: 200, default: 50 } }
responses:
'200':
description: 客户候选
content: { application/json: { schema: { $ref: '#/components/schemas/CustomerOptionResponse' } } }
/api/platform/v1/last-leg/overseas-procurements/warehouse-options:
get:
summary: 查询启用的海外合作采购仓候选
description: 权限 platform:overseas-business:purchase:list;复用服务端缓存目录,浏览器不访问国内内部 API。
security: [{ bearerAuth: [] }]
responses:
'200':
description: 采购仓候选
content: { application/json: { schema: { $ref: '#/components/schemas/WarehouseOptionResponse' } } }
/api/platform/v1/last-leg/overseas-procurements/{orderNo}:
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
get:
summary: 查询海外采购订单详情及操作流水
description: 权限 platform:overseas-business:purchase:list。
security: [{ bearerAuth: [] }]
responses: { '200': { description: 统一 ApiResponse 包装的采购订单详情 } }
patch:
summary: 编辑海外采购订单
description: 权限 platform:overseas-business:purchase:edit;可选字段缺失表示不修改,显式 null 或空串表示清空。采购仓名称由 warehouse ID 对应候选快照决定。采购出库不属于本 API。
security: [{ bearerAuth: [] }]
requestBody:
required: true
content: { application/json: { schema: { $ref: '#/components/schemas/ProcurementUpdate' } } }
responses: { '200': { description: 统一 ApiResponse 包装的采购订单详情 }, '409': { description: 乐观锁冲突或状态不允许 } }
/api/platform/v1/last-leg/overseas-procurements/{orderNo}/review:
post:
summary: 审核海外采购订单
description: 权限 platform:overseas-business:purchase:review。
security: [{ bearerAuth: [] }]
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
requestBody:
required: true
content: { application/json: { schema: { type: object, required: [decision], properties: { decision: { type: string, enum: [APPROVE, REJECT] }, remark: { type: string, nullable: true, maxLength: 1000 } } } } }
responses: { '200': { description: 统一 ApiResponse 包装的采购订单详情 } }
/api/merchant/v1/last-leg/overseas-procurements:
post:
summary: 客户创建海外采购订单
description: 客户 ID 只取认证身份;新单固定进入 PENDING_REVIEW。
security: [{ bearerAuth: [] }]
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/ProcurementCreate' } } } }
responses: { '200': { description: 统一 ApiResponse 包装的采购订单详情 } }
get:
summary: 客户分页查询自己的海外采购订单
security: [{ bearerAuth: [] }]
responses: { '200': { description: 统一 ApiResponse 包装的采购订单分页 } }
/api/merchant/v1/last-leg/overseas-procurements/{orderNo}:
get:
summary: 客户查询自己的海外采购订单详情及流水
security: [{ bearerAuth: [] }]
parameters: [{ name: orderNo, in: path, required: true, schema: { type: string } }]
responses: { '200': { description: 统一 ApiResponse 包装的采购订单详情 } }
/api/platform/v1/last-leg/us-truck-orders:
get:
summary: 分页查询本土卡车订单
description: 权限 platform:overseas-business:truck:list。
security: [{ bearerAuth: [] }]
responses: { '200': { description: 统一 ApiResponse 包装的卡车订单分页 } }
post:
summary: 平台为指定客户创建本土卡车订单
description: 权限 platform:overseas-business:truck:create;customerId 必填且只作为可信服务端隔离键。
security: [{ bearerAuth: [] }]
parameters: [{ name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }]
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/TruckCreate' } } } }
responses: { '200': { description: 统一 ApiResponse 包装的卡车订单详情 } }
/api/platform/v1/last-leg/us-truck-orders/{orderNo}:
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
get:
summary: 查询本土卡车订单详情
description: 权限 platform:overseas-business:truck:list。
security: [{ bearerAuth: [] }]
responses: { '200': { description: 统一 ApiResponse 包装的卡车订单详情 } }
patch:
summary: 平台普通编辑本土卡车订单
description: 权限 platform:overseas-business:truck:edit;仅待审核订单可编辑,不能修改状态。
security: [{ bearerAuth: [] }]
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/TruckUpdate' } } } }
responses: { '200': { description: 统一 ApiResponse 包装的卡车订单详情 } }
/api/platform/v1/last-leg/us-truck-orders/{orderNo}/status:
patch:
summary: 推进本土卡车订单状态
description: 权限 platform:overseas-business:truck:status;普通编辑接口不能修改状态。
security: [{ bearerAuth: [] }]
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
requestBody: { required: true, content: { application/json: { schema: { type: object, required: [version, status], properties: { version: { type: integer, format: int64, minimum: 0 }, status: { $ref: '#/components/schemas/TruckStatus' }, remark: { type: string, nullable: true, maxLength: 1000 } } } } } }
responses: { '200': { description: 统一 ApiResponse 包装的卡车订单详情 }, '409': { description: 非法状态迁移 } }
/api/platform/v1/last-leg/us-truck-orders/{orderNo}/receive-pallets:
post:
summary: 记录本土卡车订单实收托盘
description: 权限 platform:overseas-business:truck:status;幂等记录实收,不创建海外仓出库或派送单。
security: [{ bearerAuth: [] }]
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
responses: { '200': { description: 统一 ApiResponse 包装的卡车订单详情 } }
/api/platform/v1/last-leg/local-looseboard-orders:
get:
summary: 分页查询本土散板订单
description: 权限 platform:overseas-business:looseboard:list。
security: [{ bearerAuth: [] }]
responses: { '200': { description: 统一 ApiResponse 包装的散板订单分页 } }
post:
summary: 创建本土散板订单
description: 权限 platform:overseas-business:looseboard:create;独立稳定子域,不复用卡车端点。
security: [{ bearerAuth: [] }]
parameters: [{ name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }]
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/LooseboardCreate' } } } }
responses: { '200': { description: 统一 ApiResponse 包装的散板订单详情 } }
/api/platform/v1/last-leg/local-looseboard-orders/{orderNo}:
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
get:
summary: 查询本土散板订单详情及操作流水
description: 权限 platform:overseas-business:looseboard:list。
security: [{ bearerAuth: [] }]
responses: { '200': { description: 统一 ApiResponse 包装的散板订单详情 } }
put:
summary: 全量更新待接单的本土散板订单
description: 权限 platform:overseas-business:looseboard:edit;可空字段传 null 或空串即清空;状态由独立端点推进。
security: [{ bearerAuth: [] }]
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/LooseboardUpdate' } } } }
responses: { '200': { description: 统一 ApiResponse 包装的散板订单详情 }, '409': { description: 版本或状态冲突 } }
/api/platform/v1/last-leg/local-looseboard-orders/{orderNo}/status:
patch:
summary: 推进或取消本土散板订单
description: 权限 platform:overseas-business:looseboard:status;只允许 PENDING_ACCEPTANCE→DISPATCHED→IN_TRANSIT→COMPLETED,未完成节点按规则取消。
security: [{ bearerAuth: [] }]
parameters:
- { name: orderNo, in: path, required: true, schema: { type: string } }
- { name: customerId, in: query, required: true, schema: { type: string, pattern: '^[1-9][0-9]*$' } }
requestBody: { required: true, content: { application/json: { schema: { type: object, required: [version, status], properties: { version: { type: integer, format: int64, minimum: 0 }, status: { $ref: '#/components/schemas/LooseboardStatus' }, remark: { type: string, nullable: true, maxLength: 1000 } } } } } }
responses: { '200': { description: 统一 ApiResponse 包装的散板订单详情 }, '409': { description: 非法状态迁移 } }
components:
schemas:
ProcurementStatus: { type: string, enum: [PENDING_REVIEW, APPROVED, REJECTED] }
ProcurementCreate:
type: object
required: [purchaseCategory, productName, purchaseQuantity, contactName, contactPhone, idempotencyKey]
properties:
customerName: { type: string, nullable: true, maxLength: 255 }
purchaseCategory: { type: string, maxLength: 128 }
productName: { type: string, maxLength: 255 }
productSpecification: { type: string, nullable: true, maxLength: 500 }
productUrl: { type: string, nullable: true, maxLength: 2000 }
purchaseQuantity: { type: integer, format: int64, minimum: 1 }
budgetUnitPrice: { type: number, nullable: true, minimum: 0 }
currency: { type: string, minLength: 3, maxLength: 3, default: USD }
receivingAddress: { type: string, nullable: true, maxLength: 1000 }
contactName: { type: string, maxLength: 128 }
contactPhone: { type: string, maxLength: 64 }
remark: { type: string, nullable: true, maxLength: 1000 }
idempotencyKey: { type: string, maxLength: 255 }
NullableTextPatch: { type: string, nullable: true, description: 缺失不修改;null 或空串清空 }
ProcurementUpdate:
type: object
required: [version]
properties:
version: { type: integer, format: int64, minimum: 0 }
purchaseCategory: { type: string, maxLength: 128 }
productName: { type: string, maxLength: 255 }
productSpecification: { $ref: '#/components/schemas/NullableTextPatch' }
productUrl: { $ref: '#/components/schemas/NullableTextPatch' }
inboundQuantity: { type: integer, format: int64, minimum: 0 }
purchaseWarehouseId: { $ref: '#/components/schemas/NullableTextPatch' }
purchaseWarehouseName: { $ref: '#/components/schemas/NullableTextPatch' }
domesticCarrier: { $ref: '#/components/schemas/NullableTextPatch' }
domesticTrackingNo: { $ref: '#/components/schemas/NullableTextPatch' }
overseasCarrier: { $ref: '#/components/schemas/NullableTextPatch' }
overseasTrackingNo: { $ref: '#/components/schemas/NullableTextPatch' }
estimatedArrivalAt: { type: string, format: date-time, nullable: true, description: 缺失不修改;null 或空串清空 }
remark: { $ref: '#/components/schemas/NullableTextPatch' }
CustomerOptionResponse:
type: object
properties:
code: { type: string, enum: ['200'] }
data: { type: array, items: { type: object, properties: { customerId: { type: string }, customerName: { type: string } } } }
WarehouseOptionResponse:
type: object
properties:
code: { type: string, enum: ['200'] }
data: { type: array, items: { type: object, properties: { warehouseId: { type: string }, warehouseCode: { type: string }, warehouseName: { type: string }, countryCode: { type: string } } } }
TruckStatus: { type: string, enum: [PENDING_REVIEW, WAITING_INBOUND, RECEIVING, WAITING_CONSOLIDATION, PALLET_OVERAGE_REVIEW, PARTIALLY_ALLOCATED, ALLOCATED, PENDING_DISPATCH, DISPATCHED, IN_TRANSIT, COMPLETED, REJECTED, CANCELLED] }
TruckCreate:
type: object
required: [origin, destination, palletCount, totalWeightKg, totalVolumeCbm, contactName, contactInfo, requestedDate, idempotencyKey]
properties:
transportType: { type: string, enum: [PORT_PICKUP, WAREHOUSE_TO_WAREHOUSE, WAREHOUSE_TO_DOOR] }
origin: { type: string, maxLength: 255 }
originAddress: { type: string, nullable: true, maxLength: 500 }
destination: { type: string, maxLength: 255 }
destinationAddress: { type: string, nullable: true, maxLength: 500 }
containerType: { type: string, nullable: true, maxLength: 32 }
palletCount: { type: integer, minimum: 1 }
packageCount: { type: integer, nullable: true, minimum: 0 }
totalWeightKg: { type: number, minimum: 0 }
totalVolumeCbm: { type: number, minimum: 0 }
budgetAmount: { type: number, nullable: true, minimum: 0 }
currency: { type: string, minLength: 3, maxLength: 3, default: USD }
contactName: { type: string, maxLength: 128 }
contactInfo: { type: string, maxLength: 128 }
requestedDate: { type: string, format: date }
remark: { type: string, nullable: true, maxLength: 1000 }
idempotencyKey: { type: string, maxLength: 255 }
TruckUpdate:
type: object
required: [version]
properties:
version: { type: integer, format: int64, minimum: 0 }
transportType: { type: string, enum: [PORT_PICKUP, WAREHOUSE_TO_WAREHOUSE, WAREHOUSE_TO_DOOR] }
origin: { type: string, maxLength: 255 }
originAddress: { type: string, nullable: true, maxLength: 500 }
destination: { type: string, maxLength: 255 }
destinationAddress: { type: string, nullable: true, maxLength: 500 }
containerType: { type: string, nullable: true, maxLength: 32 }
palletCount: { type: integer, minimum: 1 }
packageCount: { type: integer, minimum: 0 }
totalWeightKg: { type: number, minimum: 0 }
totalVolumeCbm: { type: number, minimum: 0 }
budgetAmount: { type: number, nullable: true, minimum: 0 }
currency: { type: string, minLength: 3, maxLength: 3 }
contactName: { type: string, maxLength: 128 }
contactInfo: { type: string, maxLength: 128 }
requestedDate: { type: string, format: date }
remark: { type: string, nullable: true, maxLength: 1000 }
LooseboardStatus: { type: string, enum: [PENDING_ACCEPTANCE, DISPATCHED, IN_TRANSIT, COMPLETED, CANCELLED] }
LooseboardCreate:
type: object
required: [transportMode, palletRequired, transportType, origin, destination, packageCount, totalWeightKg, totalVolumeCbm, idempotencyKey]
properties:
transportMode: { type: string, enum: [SHARED_TRUCK, PRIORITY_CONSOLIDATION] }
palletRequired: { type: string, enum: [YES, NO] }
transportType: { type: string, enum: [PORT_PICKUP, WAREHOUSE_TO_WAREHOUSE, WAREHOUSE_TO_DOOR] }
origin: { type: string, maxLength: 255 }
originAddress: { type: string, nullable: true, maxLength: 500 }
destination: { type: string, maxLength: 255 }
destinationAddress: { type: string, nullable: true, maxLength: 500 }
containerType: { type: string, nullable: true, maxLength: 32 }
packageCount: { type: integer, minimum: 0 }
totalWeightKg: { type: number, minimum: 0 }
totalVolumeCbm: { type: number, minimum: 0 }
budgetAmount: { type: number, nullable: true, minimum: 0 }
currency: { type: string, minLength: 3, maxLength: 3, default: USD }
contactName: { type: string, nullable: true, maxLength: 128 }
contactInfo: { type: string, nullable: true, maxLength: 128 }
requestedDate: { type: string, format: date, nullable: true }
remark: { type: string, nullable: true, maxLength: 1000 }
idempotencyKey: { type: string, maxLength: 255 }
LooseboardUpdate:
type: object
required: [version, transportMode, palletRequired, transportType, origin, destination, packageCount, totalWeightKg, totalVolumeCbm]
properties:
version: { type: integer, format: int64, minimum: 0 }
transportMode: { type: string, enum: [SHARED_TRUCK, PRIORITY_CONSOLIDATION] }
palletRequired: { type: string, enum: [YES, NO] }
transportType: { type: string, enum: [PORT_PICKUP, WAREHOUSE_TO_WAREHOUSE, WAREHOUSE_TO_DOOR] }
origin: { type: string, maxLength: 255 }
originAddress: { type: string, nullable: true, maxLength: 500 }
destination: { type: string, maxLength: 255 }
destinationAddress: { type: string, nullable: true, maxLength: 500 }
containerType: { type: string, nullable: true, maxLength: 32 }
packageCount: { type: integer, minimum: 0 }
totalWeightKg: { type: number, minimum: 0 }
totalVolumeCbm: { type: number, minimum: 0 }
budgetAmount: { type: number, nullable: true, minimum: 0 }
currency: { type: string, minLength: 3, maxLength: 3, default: USD }
contactName: { type: string, nullable: true, maxLength: 128 }
contactInfo: { type: string, nullable: true, maxLength: 128 }
requestedDate: { type: string, format: date, nullable: true }
remark: { type: string, nullable: true, maxLength: 1000 }
securitySchemes:
bearerAuth: { type: http, scheme: bearer, bearerFormat: JWT }
@@ -0,0 +1,273 @@
openapi: 3.0.3
info:
title: Lastleg Overseas Master Data API
version: 1.0.0
description: 海外仓报价、月度汇率与车辆主数据;车辆契约不包含派送履约历史。
paths:
/api/platform/v1/last-leg/master-data/overseas-quotes:
get:
summary: 分页查询海外仓报价
description: '权限:platform:overseas-master-data:quote:list'
parameters:
- $ref: '#/components/parameters/Page'
- $ref: '#/components/parameters/Size'
- { name: keyword, in: query, schema: { type: string } }
- { name: warehouseId, in: query, schema: { type: string } }
- { name: providerName, in: query, schema: { type: string } }
- { name: currency, in: query, schema: { type: string } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/ActiveStatus' } }
responses: { '200': { description: 业务响应,data为PageResult<QuoteSummary> } }
post:
summary: 创建海外仓报价
description: '权限:platform:overseas-master-data:quote:create;服务端读取国内overseas-partners并缓存合作仓目录30分钟'
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/QuoteCreate' } } } }
responses: { '200': { description: 业务响应,data为报价详情 } }
/api/platform/v1/last-leg/master-data/overseas-quotes/warehouse-options:
get:
summary: 查询缓存的有效海外合作仓选项
description: '权限:platform:overseas-master-data:quote:list;浏览器不直接调用国内内部接口'
responses: { '200': { description: 业务响应 } }
/api/platform/v1/last-leg/master-data/overseas-quotes/export:
get:
summary: 导出海外仓报价
description: '权限:platform:overseas-master-data:quote:export;UTF-8 BOM CSV'
parameters:
- { name: keyword, in: query, schema: { type: string } }
- { name: warehouseId, in: query, schema: { type: string } }
- { name: providerName, in: query, schema: { type: string } }
- { name: currency, in: query, schema: { type: string } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/ActiveStatus' } }
responses: { '200': { description: CSV, content: { text/csv: { schema: { type: string, format: binary } } } } }
/api/platform/v1/last-leg/master-data/overseas-quotes/{id}:
parameters:
- { name: id, in: path, required: true, schema: { type: integer, format: int64 } }
get:
summary: 查询海外仓报价详情
description: '权限:platform:overseas-master-data:quote:list'
responses: { '200': { description: 业务响应 } }
put:
summary: 编辑未生效的海外仓报价
description: '权限:platform:overseas-master-data:quote:edit;recordVersion乐观锁'
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/QuoteUpdate' } } } }
responses: { '200': { description: 业务响应 } }
/api/platform/v1/last-leg/master-data/overseas-quotes/{id}/status:
patch:
summary: 启停海外仓报价
description: '权限:platform:overseas-master-data:quote:status'
parameters:
- { name: id, in: path, required: true, schema: { type: integer, format: int64 } }
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/QuoteStatusChange' } } } }
responses: { '200': { description: 业务响应 } }
/api/platform/v1/last-leg/master-data/exchange-rates:
get:
summary: 分页查询月度汇率
description: '权限:platform:overseas-master-data:exchange-rate:list'
parameters:
- $ref: '#/components/parameters/Page'
- $ref: '#/components/parameters/Size'
- { name: monthFrom, in: query, schema: { type: string, pattern: '^\d{4}-(0[1-9]|1[0-2])$' } }
- { name: monthTo, in: query, schema: { type: string, pattern: '^\d{4}-(0[1-9]|1[0-2])$' } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/ActiveStatus' } }
responses: { '200': { description: 业务响应,data为PageResult<MonthlyExchangeRate> } }
post:
summary: 创建月度汇率
description: '权限:platform:overseas-master-data:exchange-rate:create;月份唯一,初始状态ACTIVE'
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/ExchangeRateCreate' } } } }
responses: { '200': { description: 业务响应,data为MonthlyExchangeRate } }
/api/platform/v1/last-leg/master-data/exchange-rates/summary:
get:
summary: 查询最新有效月度汇率摘要
description: '权限:platform:overseas-master-data:exchange-rate:list'
responses: { '200': { description: 业务响应,data含latestMonth/latestUsdToCnyAverage/updatedBy/updatedAt } }
/api/platform/v1/last-leg/master-data/exchange-rates/export:
get:
summary: 导出筛选后的全部月度汇率
description: '权限:platform:overseas-master-data:exchange-rate:export;UTF-8 BOM CSV'
parameters:
- { name: monthFrom, in: query, schema: { type: string } }
- { name: monthTo, in: query, schema: { type: string } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/ActiveStatus' } }
responses: { '200': { description: CSV, content: { text/csv: { schema: { type: string, format: binary } } } } }
/api/platform/v1/last-leg/master-data/exchange-rates/{month}:
parameters:
- { name: month, in: path, required: true, schema: { type: string, pattern: '^\d{4}-(0[1-9]|1[0-2])$' } }
get:
summary: 查询月度汇率详情
description: '权限:platform:overseas-master-data:exchange-rate:list'
responses: { '200': { description: 业务响应,data为MonthlyExchangeRate } }
put:
summary: 编辑月度汇率
description: '权限:platform:overseas-master-data:exchange-rate:edit;recordVersion冲突返回业务错误'
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/ExchangeRateUpdate' } } } }
responses: { '200': { description: 业务响应 } }
/api/platform/v1/last-leg/master-data/exchange-rates/{month}/status:
patch:
summary: 变更月度汇率状态
description: '权限:platform:overseas-master-data:exchange-rate:status'
parameters:
- { name: month, in: path, required: true, schema: { type: string } }
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/ExchangeRateStatus' } } } }
responses: { '200': { description: 业务响应 } }
/api/platform/v1/last-leg/master-data/vehicles:
get:
summary: 分页查询车辆主数据
description: '权限:platform:overseas-master-data:vehicle:list'
parameters:
- $ref: '#/components/parameters/Page'
- $ref: '#/components/parameters/Size'
- { name: keyword, in: query, description: 车牌/车型/司机或外派单位, schema: { type: string } }
- { name: ownership, in: query, schema: { $ref: '#/components/schemas/VehicleOwnership' } }
- { name: region, in: query, schema: { $ref: '#/components/schemas/VehicleRegion' } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/VehicleStatus' } }
responses: { '200': { description: 业务响应,data为PageResult<Vehicle> } }
post:
summary: 创建车辆主数据
description: '权限:platform:overseas-master-data:vehicle:create;车牌号唯一'
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/VehicleCreate' } } } }
responses: { '200': { description: 业务响应,data为Vehicle } }
/api/platform/v1/last-leg/master-data/vehicles/export:
get:
summary: 导出筛选后的全部车辆主数据
description: '权限:platform:overseas-master-data:vehicle:export;UTF-8 BOM CSV'
parameters:
- { name: keyword, in: query, schema: { type: string } }
- { name: ownership, in: query, schema: { $ref: '#/components/schemas/VehicleOwnership' } }
- { name: region, in: query, schema: { $ref: '#/components/schemas/VehicleRegion' } }
- { name: status, in: query, schema: { $ref: '#/components/schemas/VehicleStatus' } }
responses: { '200': { description: CSV, content: { text/csv: { schema: { type: string, format: binary } } } } }
/api/platform/v1/last-leg/master-data/vehicles/{id}:
parameters:
- { name: id, in: path, required: true, schema: { type: integer, format: int64 } }
get:
summary: 查询车辆档案详情
description: '权限:platform:overseas-master-data:vehicle:list;不包含派送履约或车辆更换历史'
responses: { '200': { description: 业务响应,data为Vehicle } }
put:
summary: 编辑车辆主数据
description: '权限:platform:overseas-master-data:vehicle:edit;状态由独立接口变更'
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/VehicleUpdate' } } } }
responses: { '200': { description: 业务响应 } }
/api/platform/v1/last-leg/master-data/vehicles/{id}/status:
patch:
summary: 变更车辆状态
description: '权限:platform:overseas-master-data:vehicle:status;使用recordVersion乐观锁'
parameters:
- { name: id, in: path, required: true, schema: { type: integer, format: int64 } }
requestBody: { required: true, content: { application/json: { schema: { $ref: '#/components/schemas/VehicleStatusChange' } } } }
responses: { '200': { description: 业务响应 } }
components:
parameters:
Page: { name: page, in: query, schema: { type: integer, minimum: 1, default: 1 } }
Size: { name: size, in: query, schema: { type: integer, minimum: 1, maximum: 200, default: 20 } }
schemas:
ActiveStatus: { type: string, enum: [ACTIVE, INACTIVE] }
QuoteFee:
type: object
required: [item, billingUnit, unitPrice]
properties:
item: { type: string, maxLength: 128 }
billingUnit: { type: string, maxLength: 64 }
unitPrice: { type: number, minimum: 0 }
minimumCharge: { type: number, minimum: 0, nullable: true }
remark: { type: string, maxLength: 500, nullable: true }
QuoteTransitPrice:
type: object
required: [fbaWarehouseCode, deliveryMethod, price]
properties:
fbaWarehouseCode: { type: string, maxLength: 64 }
deliveryMethod: { type: string, maxLength: 64 }
estimatedMiles: { type: number, minimum: 0, nullable: true }
price: { type: number, minimum: 0 }
minimumCharge: { type: number, minimum: 0, nullable: true }
remark: { type: string, maxLength: 500, nullable: true }
QuoteCreate:
type: object
required: [name, warehouseId, providerName, currency, effectiveStart, effectiveEnd, versionCode, warehouseFees]
properties:
name: { type: string, maxLength: 128 }
warehouseId: { type: string, description: 国内平台海外合作仓ID }
providerName: { type: string, maxLength: 128 }
currency: { type: string, minLength: 3, maxLength: 3 }
effectiveStart: { type: string, format: date }
effectiveEnd: { type: string, format: date }
versionCode: { type: string, maxLength: 64 }
warehouseFees: { type: array, minItems: 1, items: { $ref: '#/components/schemas/QuoteFee' } }
transitPrices: { type: array, items: { $ref: '#/components/schemas/QuoteTransitPrice' } }
remark: { type: string, maxLength: 1000, nullable: true }
QuoteUpdate:
type: object
required: [recordVersion, name, providerName, currency, effectiveStart, effectiveEnd, warehouseFees]
properties:
recordVersion: { type: integer, format: int64, minimum: 0 }
name: { type: string, maxLength: 128 }
providerName: { type: string, maxLength: 128 }
currency: { type: string, minLength: 3, maxLength: 3 }
effectiveStart: { type: string, format: date }
effectiveEnd: { type: string, format: date }
warehouseFees: { type: array, minItems: 1, items: { $ref: '#/components/schemas/QuoteFee' } }
transitPrices: { type: array, items: { $ref: '#/components/schemas/QuoteTransitPrice' } }
remark: { type: string, maxLength: 1000, nullable: true }
QuoteStatusChange:
type: object
required: [status, recordVersion]
properties:
status: { $ref: '#/components/schemas/ActiveStatus' }
recordVersion: { type: integer, format: int64, minimum: 0 }
ExchangeRateCreate:
type: object
required: [month, usdToCnyAverage]
properties:
month: { type: string, example: '2026-08' }
usdToCnyAverage: { type: number, exclusiveMinimum: true, minimum: 0, example: 7.18540000 }
remark: { type: string, maxLength: 1000, nullable: true }
ExchangeRateUpdate:
type: object
required: [recordVersion, usdToCnyAverage]
properties:
recordVersion: { type: integer, format: int64, minimum: 0 }
usdToCnyAverage: { type: number, exclusiveMinimum: true, minimum: 0 }
remark: { type: string, maxLength: 1000, nullable: true }
ExchangeRateStatus:
type: object
required: [status, recordVersion]
properties:
status: { $ref: '#/components/schemas/ActiveStatus' }
recordVersion: { type: integer, format: int64, minimum: 0 }
remark: { type: string, maxLength: 500, nullable: true }
VehicleOwnership: { type: string, enum: [OWNED, DISPATCHED] }
VehicleRegion: { type: string, enum: [DOMESTIC, OVERSEAS] }
VehicleStatus: { type: string, enum: [IN_SERVICE, DISPATCHED, MAINTENANCE, INACTIVE, RETURNED] }
VehicleCreate:
type: object
required: [plateNumber, model, fuelConsumptionPer100Km, mileageKm, region, ownership, status]
properties:
plateNumber: { type: string, maxLength: 64 }
model: { type: string, maxLength: 128 }
fuelConsumptionPer100Km: { type: number, exclusiveMinimum: true, minimum: 0 }
mileageKm: { type: integer, format: int64, minimum: 0 }
driverOrDispatchCompany: { type: string, maxLength: 128, nullable: true }
phone: { type: string, maxLength: 64, nullable: true }
region: { $ref: '#/components/schemas/VehicleRegion' }
ownership: { $ref: '#/components/schemas/VehicleOwnership' }
status: { $ref: '#/components/schemas/VehicleStatus' }
remark: { type: string, maxLength: 1000, nullable: true }
VehicleUpdate:
type: object
required: [recordVersion, plateNumber, model, fuelConsumptionPer100Km, mileageKm, region, ownership]
properties:
recordVersion: { type: integer, format: int64, minimum: 0 }
plateNumber: { type: string, maxLength: 64 }
model: { type: string, maxLength: 128 }
fuelConsumptionPer100Km: { type: number, exclusiveMinimum: true, minimum: 0 }
mileageKm: { type: integer, format: int64, minimum: 0, description: 不得小于已有公里码 }
driverOrDispatchCompany: { type: string, maxLength: 128, nullable: true }
phone: { type: string, maxLength: 64, nullable: true }
region: { $ref: '#/components/schemas/VehicleRegion' }
ownership: { $ref: '#/components/schemas/VehicleOwnership' }
remark: { type: string, maxLength: 1000, nullable: true }
VehicleStatusChange:
type: object
required: [status, recordVersion]
properties:
status: { $ref: '#/components/schemas/VehicleStatus' }
recordVersion: { type: integer, format: int64, minimum: 0 }