对接文档重构:两种发货对接方式分开展示
- 左侧目录按分组展示:基础接口 / 发货链接模式 / 自建发货页模式 / 回调 / 附录 - 概述页发货对接方式对比表强化(适用场景/接口顺序/建议) - 创建订单响应示例 data 统一为约定字段,补充 201/200 状态说明 - 对外响应字段 upstream_order 更名为 delivery(result_data 存储键兼容旧数据)
This commit is contained in:
@@ -48,7 +48,10 @@ func deliverySubmittedUpstream(order *model.FulfillmentOrder) bool {
|
|||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
m := resultDataMap(order.ResultData)
|
m := resultDataMap(order.ResultData)
|
||||||
if _, ok := m["upstream_order"]; ok {
|
if _, ok := m["delivery"]; ok {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
if _, ok := m["upstream_order"]; ok { // 兼容历史数据
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
return resultDataString(order.ResultData, "provider_order_stage") == deliveryStageSubmitted
|
return resultDataString(order.ResultData, "provider_order_stage") == deliveryStageSubmitted
|
||||||
@@ -144,7 +147,7 @@ type DeliverySubmitResult struct {
|
|||||||
Message string `json:"message"`
|
Message string `json:"message"`
|
||||||
ProviderOrderNo string `json:"provider_order_no,omitempty"`
|
ProviderOrderNo string `json:"provider_order_no,omitempty"`
|
||||||
GameAccount map[string]interface{} `json:"game_account,omitempty"`
|
GameAccount map[string]interface{} `json:"game_account,omitempty"`
|
||||||
UpstreamOrder interface{} `json:"upstream_order,omitempty"`
|
UpstreamOrder interface{} `json:"delivery,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type DeliveryLinkAuth struct {
|
type DeliveryLinkAuth struct {
|
||||||
@@ -348,7 +351,7 @@ func (s *DeliveryService) submit(orderNo, gameAccount, bindUUID string, apiClien
|
|||||||
"game_uid": gameAccount,
|
"game_uid": gameAccount,
|
||||||
"role_name": stringFromMap(boundAccount, "game_account_role_name"),
|
"role_name": stringFromMap(boundAccount, "game_account_role_name"),
|
||||||
"game_channel": gameChannelText(boundAccount),
|
"game_channel": gameChannelText(boundAccount),
|
||||||
"upstream_order": upstreamOrder,
|
"delivery": upstreamOrder,
|
||||||
})
|
})
|
||||||
nextStatus := model.OrderStatusDelivering
|
nextStatus := model.OrderStatusDelivering
|
||||||
message := "已提交发货,等待发货结果回传"
|
message := "已提交发货,等待发货结果回传"
|
||||||
|
|||||||
@@ -67,7 +67,7 @@ const orderResponseExample = `{
|
|||||||
"amount": 105,
|
"amount": 105,
|
||||||
"currency": "POINT",
|
"currency": "POINT",
|
||||||
"buyer_reference": "buyer-001",
|
"buyer_reference": "buyer-001",
|
||||||
"data": { "server": "ios-wechat", "uid": "player-id" },
|
"data": { "game_account": "4808146277", "game_channel": "ios-wechat" },
|
||||||
"provider_order_no": "",
|
"provider_order_no": "",
|
||||||
"failure_reason": "",
|
"failure_reason": "",
|
||||||
"created_at": "2026-07-30T10:00:00+08:00",
|
"created_at": "2026-07-30T10:00:00+08:00",
|
||||||
@@ -133,7 +133,7 @@ const deliverySubmitResponseExample = `{
|
|||||||
"game_account": "4808146277",
|
"game_account": "4808146277",
|
||||||
"game_account_role_name": "巫师哈丁12"
|
"game_account_role_name": "巫师哈丁12"
|
||||||
},
|
},
|
||||||
"upstream_order": {
|
"delivery": {
|
||||||
"order_no": "provider-1"
|
"order_no": "provider-1"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -142,6 +142,7 @@ const deliverySubmitResponseExample = `{
|
|||||||
export const endpoints: EndpointSpec[] = [
|
export const endpoints: EndpointSpec[] = [
|
||||||
{
|
{
|
||||||
key: 'list-products',
|
key: 'list-products',
|
||||||
|
group: 'basic',
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
path: '/api/client/v1/products',
|
path: '/api/client/v1/products',
|
||||||
title: '商品列表',
|
title: '商品列表',
|
||||||
@@ -187,6 +188,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'create-order',
|
key: 'create-order',
|
||||||
|
group: 'basic',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
path: '/api/client/v1/orders',
|
path: '/api/client/v1/orders',
|
||||||
title: '创建订单',
|
title: '创建订单',
|
||||||
@@ -225,7 +227,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
"amount": 105,
|
"amount": 105,
|
||||||
"currency": "POINT",
|
"currency": "POINT",
|
||||||
"buyer_reference": "buyer-001",
|
"buyer_reference": "buyer-001",
|
||||||
"data": { "server": "ios-wechat", "uid": "player-id" },
|
"data": { "game_account": "4808146277", "game_channel": "ios-wechat" },
|
||||||
"provider_order_no": "",
|
"provider_order_no": "",
|
||||||
"failure_reason": "",
|
"failure_reason": "",
|
||||||
"created_at": "2026-07-30T10:00:00+08:00",
|
"created_at": "2026-07-30T10:00:00+08:00",
|
||||||
@@ -239,6 +241,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
{ name: 'order', type: 'object', desc: '订单完整对象,字段见下方「订单字段说明」' },
|
{ name: 'order', type: 'object', desc: '订单完整对象,字段见下方「订单字段说明」' },
|
||||||
],
|
],
|
||||||
notes: [
|
notes: [
|
||||||
|
'成功创建返回 HTTP 201;命中幂等(client_order_no 已存在)返回 HTTP 200 且 idempotent=true。',
|
||||||
'client_order_no 是唯一幂等单号,请保证同一商户下不重复;重复请求不会重复扣款,返回 idempotent=true 及既有订单。',
|
'client_order_no 是唯一幂等单号,请保证同一商户下不重复;重复请求不会重复扣款,返回 idempotent=true 及既有订单。',
|
||||||
'当前无真实支付流程,下单成功即扣款并进入 order_status=paid,余额不足返回 400。',
|
'当前无真实支付流程,下单成功即扣款并进入 order_status=paid,余额不足返回 400。',
|
||||||
'下单成功后请保存 order_no,后续查询/发货/回调均以 order_no 为准;client_order_no 仅用于幂等。',
|
'下单成功后请保存 order_no,后续查询/发货/回调均以 order_no 为准;client_order_no 仅用于幂等。',
|
||||||
@@ -247,6 +250,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'query-order',
|
key: 'query-order',
|
||||||
|
group: 'basic',
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
path: '/api/client/v1/orders/{order_no}',
|
path: '/api/client/v1/orders/{order_no}',
|
||||||
title: '查询订单',
|
title: '查询订单',
|
||||||
@@ -258,6 +262,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'cancel-order',
|
key: 'cancel-order',
|
||||||
|
group: 'basic',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
path: '/api/client/v1/orders/{order_no}/cancel',
|
path: '/api/client/v1/orders/{order_no}/cancel',
|
||||||
title: '取消订单',
|
title: '取消订单',
|
||||||
@@ -275,6 +280,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'delivery-link',
|
key: 'delivery-link',
|
||||||
|
group: 'delivery-link',
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
path: '/api/client/v1/orders/{order_no}/delivery-link',
|
path: '/api/client/v1/orders/{order_no}/delivery-link',
|
||||||
title: '获取发货链接',
|
title: '获取发货链接',
|
||||||
@@ -296,6 +302,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'delivery-order',
|
key: 'delivery-order',
|
||||||
|
group: 'delivery-self',
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
path: '/api/client/v1/orders/{order_no}/delivery',
|
path: '/api/client/v1/orders/{order_no}/delivery',
|
||||||
title: '查询发货数据',
|
title: '查询发货数据',
|
||||||
@@ -328,6 +335,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'delivery-bind',
|
key: 'delivery-bind',
|
||||||
|
group: 'delivery-self',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
path: '/api/client/v1/orders/{order_no}/delivery/bind',
|
path: '/api/client/v1/orders/{order_no}/delivery/bind',
|
||||||
title: '发起绑定',
|
title: '发起绑定',
|
||||||
@@ -353,6 +361,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'delivery-submit',
|
key: 'delivery-submit',
|
||||||
|
group: 'delivery-self',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
path: '/api/client/v1/orders/{order_no}/delivery/submit',
|
path: '/api/client/v1/orders/{order_no}/delivery/submit',
|
||||||
title: '提交发货',
|
title: '提交发货',
|
||||||
@@ -374,7 +383,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
{ name: 'message', type: 'string', desc: '处理结果说明' },
|
{ name: 'message', type: 'string', desc: '处理结果说明' },
|
||||||
{ name: 'provider_order_no', type: 'string', desc: '平台发货单号' },
|
{ name: 'provider_order_no', type: 'string', desc: '平台发货单号' },
|
||||||
{ name: 'game_account', type: 'object', desc: '账号绑定结果' },
|
{ name: 'game_account', type: 'object', desc: '账号绑定结果' },
|
||||||
{ name: 'upstream_order', type: 'object', desc: '发货提交结果' },
|
{ name: 'delivery', type: 'object', desc: '发货提交结果' },
|
||||||
],
|
],
|
||||||
notes: [
|
notes: [
|
||||||
'同一订单重复提交应直接返回已有结果,不应重复发起发货。',
|
'同一订单重复提交应直接返回已有结果,不应重复发起发货。',
|
||||||
@@ -383,6 +392,7 @@ export const endpoints: EndpointSpec[] = [
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
key: 'get-wallet',
|
key: 'get-wallet',
|
||||||
|
group: 'basic',
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
path: '/api/client/v1/wallet',
|
path: '/api/client/v1/wallet',
|
||||||
title: '余额查询',
|
title: '余额查询',
|
||||||
|
|||||||
@@ -16,6 +16,8 @@ export const endpointSections = [
|
|||||||
export interface EndpointSpec {
|
export interface EndpointSpec {
|
||||||
/** 唯一 key,用于折叠面板与锚点 */
|
/** 唯一 key,用于折叠面板与锚点 */
|
||||||
key: string
|
key: string
|
||||||
|
/** 接口分组:basic 基础 / delivery-link 发货链接模式 / delivery-self 自建发货页模式 */
|
||||||
|
group: 'basic' | 'delivery-link' | 'delivery-self'
|
||||||
/** HTTP 方法 */
|
/** HTTP 方法 */
|
||||||
method: HttpMethod
|
method: HttpMethod
|
||||||
/** 接口路径,路径参数用 {name} 表示 */
|
/** 接口路径,路径参数用 {name} 表示 */
|
||||||
|
|||||||
@@ -19,15 +19,18 @@ const baseUrl =
|
|||||||
|
|
||||||
const deliveryModes = [
|
const deliveryModes = [
|
||||||
{
|
{
|
||||||
mode: 'Web 发货页',
|
mode: '发货链接模式',
|
||||||
scene: '商户想要“只返回一个链接”,让用户直接打开平台页面填写 UID',
|
scene: '实现最简:下单后拿一个签名链接,直接跳转平台发货页,由买家在页面上绑定账号并提交',
|
||||||
interfaces: '/api/client/v1/orders/{order_no}/delivery-link',
|
interfaces: '/api/client/v1/orders/{order_no}/delivery-link',
|
||||||
|
steps: '下单 → 获取发货链接 → 链接给买家 → 平台页完成发货',
|
||||||
|
recommend: '商户无自建发货页、想最快上线时使用',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
mode: '自建发货页',
|
mode: '自建发货页模式',
|
||||||
scene: '商户自己有前端页面,想在自己的系统里完成发货流程',
|
scene: '商户自己有前端页面,把发货流程嵌在自己的系统里(可预填下单时透传的账号/区服)',
|
||||||
interfaces:
|
interfaces: '/api/client/v1/orders/{order_no}/delivery\n/api/client/v1/orders/{order_no}/delivery/bind\n/api/client/v1/orders/{order_no}/delivery/submit',
|
||||||
'/api/client/v1/orders/{order_no}/delivery\n/api/client/v1/orders/{order_no}/delivery/bind\n/api/client/v1/orders/{order_no}/delivery/submit',
|
steps: '下单 → 查询发货数据 → 发起绑定 → 提交发货',
|
||||||
|
recommend: '商户需要自定义发货交互(展示区服、预填账号)时使用',
|
||||||
},
|
},
|
||||||
]
|
]
|
||||||
|
|
||||||
@@ -48,6 +51,16 @@ interface TocGroup {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function buildToc(): TocGroup[] {
|
function buildToc(): TocGroup[] {
|
||||||
|
const tocItems = (eps: typeof endpoints) =>
|
||||||
|
eps.map((ep) => ({
|
||||||
|
id: `ep-${ep.key}`,
|
||||||
|
label: ep.title,
|
||||||
|
children: endpointSections.map((s) => ({
|
||||||
|
id: `ep-${ep.key}-${s.id}`,
|
||||||
|
label: s.label,
|
||||||
|
level: 3 as const,
|
||||||
|
})),
|
||||||
|
}))
|
||||||
return [
|
return [
|
||||||
{
|
{
|
||||||
title: '开始',
|
title: '开始',
|
||||||
@@ -57,16 +70,16 @@ function buildToc(): TocGroup[] {
|
|||||||
],
|
],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: '接口',
|
title: '基础接口',
|
||||||
items: endpoints.map((ep) => ({
|
items: tocItems(endpoints.filter((ep) => ep.group === 'basic')),
|
||||||
id: `ep-${ep.key}`,
|
},
|
||||||
label: ep.title,
|
{
|
||||||
children: endpointSections.map((s) => ({
|
title: '发货链接模式',
|
||||||
id: `ep-${ep.key}-${s.id}`,
|
items: tocItems(endpoints.filter((ep) => ep.group === 'delivery-link')),
|
||||||
label: s.label,
|
},
|
||||||
level: 3 as const,
|
{
|
||||||
})),
|
title: '自建发货页模式',
|
||||||
})),
|
items: tocItems(endpoints.filter((ep) => ep.group === 'delivery-self')),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: '回调',
|
title: '回调',
|
||||||
@@ -321,12 +334,12 @@ function OverviewSection() {
|
|||||||
<li>在「开放 API / API 密钥」创建凭证,获得 <Text code>AppKey</Text> 与 <Text code>AppSecret</Text>。</li>
|
<li>在「开放 API / API 密钥」创建凭证,获得 <Text code>AppKey</Text> 与 <Text code>AppSecret</Text>。</li>
|
||||||
<li>每次请求携带 <Text code>X-App-Key / X-Timestamp / X-Nonce / X-Sign</Text> 四个鉴权头。</li>
|
<li>每次请求携带 <Text code>X-App-Key / X-Timestamp / X-Nonce / X-Sign</Text> 四个鉴权头。</li>
|
||||||
<li>调用「商品列表」拿到可售 <Text code>sku</Text>,调用「下单」创建订单并扣款。</li>
|
<li>调用「商品列表」拿到可售 <Text code>sku</Text>,调用「下单」创建订单并扣款。</li>
|
||||||
<li>拿到 <Text code>order_no</Text> 后,可选择返回发货链接,或者用结构化发货接口完成自建页面流程。</li>
|
<li>拿到 <Text code>order_no</Text> 后,按「发货对接方式」二选一:发货链接模式(返回链接即可)或自建发货页模式(结构化接口)。</li>
|
||||||
<li>在「回调」页配置回调地址并订阅事件,订单状态变化会实时推送,见「回调通知」。</li>
|
<li>在「回调」页配置回调地址并订阅事件,订单状态变化会实时推送,见「回调通知」。</li>
|
||||||
</ol>
|
</ol>
|
||||||
}
|
}
|
||||||
/>
|
/>
|
||||||
<Card className="api-docs__card" size="small" title="发货链路概览">
|
<Card className="api-docs__card" size="small" title="发货对接方式(二选一,先选好再看对应接口)">
|
||||||
<Table
|
<Table
|
||||||
className="api-docs__table"
|
className="api-docs__table"
|
||||||
size="small"
|
size="small"
|
||||||
@@ -334,13 +347,20 @@ function OverviewSection() {
|
|||||||
rowKey="mode"
|
rowKey="mode"
|
||||||
dataSource={deliveryModes}
|
dataSource={deliveryModes}
|
||||||
columns={[
|
columns={[
|
||||||
{ title: '模式', dataIndex: 'mode', width: 140 },
|
{ title: '方式', dataIndex: 'mode', width: 130 },
|
||||||
{ title: '适用场景', dataIndex: 'scene' },
|
{ title: '适用场景', dataIndex: 'scene' },
|
||||||
|
{
|
||||||
|
title: '接口顺序',
|
||||||
|
dataIndex: 'steps',
|
||||||
|
width: 250,
|
||||||
|
render: (v: string) => <pre className="api-docs__pre">{v}</pre>,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
title: '相关接口',
|
title: '相关接口',
|
||||||
dataIndex: 'interfaces',
|
dataIndex: 'interfaces',
|
||||||
render: (v: string) => <pre className="api-docs__pre">{v}</pre>,
|
render: (v: string) => <pre className="api-docs__pre">{v}</pre>,
|
||||||
},
|
},
|
||||||
|
{ title: '建议', dataIndex: 'recommend', width: 170 },
|
||||||
]}
|
]}
|
||||||
/>
|
/>
|
||||||
</Card>
|
</Card>
|
||||||
|
|||||||
Reference in New Issue
Block a user