跳到主要内容

服务端对接

支付结果服务端回调

在玩家支付成功或者退款等操作后,XD SDK 会收到支付渠道的回调,平台会把支付结果和用户信息发送给游戏服务,游戏需要接收处理该消息(比如发放游戏道具给玩家 / 收回已放发的道具),并返回应答。

回调 URL:该链接由游戏服务端提供,配置到平台商户后台(可在申请开通游戏支付时在邮件或者 Jira 单一并提供,或者联系平台研发做配置)。

回调密钥:由平台后台生成,用于回调内容签名 (平台在给游戏开通支付后会提供)。

请确保回调 URL 是外部可正常访问的,且不能携带后缀参数,否则可能导致游戏服务无法接收到平台的回调通知信息。

回调 URL 示例:https://gameserver.xd.com/pay.action

通知规则

在玩家支付成功或者退款等操作后,XD SDK 会收到支付渠道的回调,平台会把支付结果和用户信息发送给游戏服务,游戏需要接收处理该消息(比如发放游戏道具给玩家 / 收回已放发的道具),并返回应答。

如果平台收到商户的应答不符合规范或超时,平台认为通知失败,会通过一定的策略定期重新发起通知,尽最大努力重试,但不保证通知最终能成功。

信息

游戏服务端需要重复通知幂等处理

重试规则如下:

回调重投策略

通知报文

支付结果通知是以 POST 方法访问游戏设置的通知 url,通知的数据以 JSON 格式通过请求主体(BODY)传输。通知的数据包括了支付结果详情。

支付成功

通知内容主体

nameDateTypeOptionsDescription
notifyIdnumberrequire通知唯一 id
notifyTimenumberrequire通知创建时间戳(毫秒)
appIdnumberrequire商户应用 id
userIdstringrequire用户 id
trxNonumberrequire平台交易单号
trxTypenumberrequire交易类型,0: 支付成功,2: 退款
outTrxNostringnullable商户交易单号(即客户端传入的 orderId)
platformnumberrequire平台,枚举值见附录
channelnumberrequire支付渠道,枚举值见附录
paymentTypenumberrequire支付方式,枚举值见附录
productsarrayrequire购买的商品列表 , 见下面说明
currencystringrequire货币
regionstringrequire地区
clientAmountdecimalnullable玩家所实际支付金额(该值为客户端上报),仅在 Google/Apple Pay 有值
clientCurrencystringnullable玩家所实际支付货币(该值为客户端上报),仅在 Google/Apple Pay 有值
clientRegionstringnullable玩家所实际支付地区(该值为客户端上报),仅在 Google/Apple Pay 有值
totalAmountdecimalrequire订单总金额
statusnumberrequire订单状态
successTimenumberrequire订单完成时间戳(毫秒)
attachobjectnullable附加数据,见下面说明
信息
  • trxType 为交易类型,0: 支付成功,2: 退款,请注意区分莫要出现把退款当成支付成功的情况
  • 有两种情况返回的 outTrxNo 并非是客户端传入的 orderId(即上面表格里的 outTrxNo),而是平台随机生成的唯一 id,所以不建议游戏服务端以 outTrxNo 是否存在为校验依据
    • Apple 支付票据有概率会出现多票据合并的情况,此时会丢失客户端传入的 orderId
    • 网页支付还有一个从游戏官网进入的版本,玩家在官网网页支付创建的订单都没有游戏客户端传入的 orderId
  • trxNo 为平台唯一订单号,游戏服务端需要记录并做好重复通知幂等处理。
  • outTrxNo 为商户订单号(官网网页充值此订单号由平台随机生成唯一 id),商户需要保证 outTrxNo 唯一性,发起充值时平台服务会根据 outTrxNo 和 appId 做幂等处理。
  • 如果客户端在调用 SDK 创建订单时未传入 outTrxNo,平台将会为该订单随机生成一个唯一的 outTrxNo。
  • outTrxNo 可以用于辅助问题排查或辅助三方对账,如果游戏有类似需求还是建议游戏客户端传入 orderId(即上面表格里的 outTrxNo)。
  • 网页充值中存在一笔订单购买多个商品的场景。
  • 对于 Google Pay、Apple Pay、和一些 web 支付渠道,totalAmount 并非用户实际付款金额,而是该商品在平台配置的金额。

支付地区

clientRegion 表示玩家实际支付的地区仅在 Google/Apple Pay 有值,并且如果遇到苹果票据合并,clientRegion 就会为空。

信息

只有等于或高于 6.8.1 版本的 iOS XD SDK 才新增获取 clientRegion 功能。SDK 低于 6.8.1 版本,服务端回调内的 clientRegion 一定为空

region 字段:

  • AS/GP 下的 region 字段是根据IP判断的
  • 网页支付锁区情况下,region 是玩家“注册地区”
  • 不锁区的情况下,region 就是玩家自己选择的地区

如下 Google Pay 回调示例: region = HK 表示通过 ip 判断,下单网络是在 HK clientRegion 则表示下单地区是 CN,使用了 clientCurrency = CNY 做的支付。

{
"bankTrxNo":"2000000281119059",
"clientAmount":29.9,
"trxNo":457171434654203905,
"clientCurrency":"CNY",
"notifyTime":1676870194264,
"channel":1,
"trxType":0,
"userId":"339464430121472000",
"outTrxNo":"D7AE0F64-DC6E-4579-82B4-1F02D3920852",
"platform":1,
"paymentType":0,
"products":[
{
"productCode":"com.xd.sdkdemo1.stone300",
"quantity":1,
"channelSkuCode":"com.tds.sdkdemopro.fxqusd299"
}
],
"clientRegion":"CN",
"totalAmount":8.99,
"appId":1111,
"successTime":1676870194228,
"currency":"USD",
"notifyId":457171562190405632,
"attach":{
"gameServerId":"999",
"gameExt":"abcdexxx",
"gameRoleId":"test-user"
},
"region":"HK",
"status":0
}

网页支付示例如下: clientRegion 为空。 在开启了网页支付锁区功能的情况,region 字段为玩家的注册地区,否则为玩家在网页上选择的地区。

{
"bankTrxNo":"20230220194010800190188000007040217",
"trxNo":457170213067358209,
"clientCurrency":"",
"notifyTime":1676869890957,
"channel":15,
"trxType":0,
"userId":"383935802234916864",
"outTrxNo":"457170214115934209",
"platform":4,
"paymentType":1,
"products":[
{
"productCode":"com.xd.sdkdemo1.stone60",
"quantity":1,
"channelSkuCode":"com.tds.sdkdemopro.fxqusd299"
}
],
"clientRegion":"",
"totalAmount":4.99,
"appId":1111,
"successTime":1676869890938,
"currency":"USD",
"notifyId":457170290028642304,
"attach":{
"gameServerId":"ap-sg",
"gameExt":"",
"gameRoleId":"383935802234916864"
},
"region":"TW",
"status":0
}

商品信息

主体内容中的 products 字段,该字段为数组。

nameDateTypeOptionsDescription
productCodestringrequire商品码
quantitynumberrequire数量
channelSkuCodestringrequire支付渠道商品码。只有 Google Pay、Apple Pay 该字段才有值

附加数据

主体内容中的 attach 字段,详细字段如下:

nameDateTypeOptionsDescription
gameServerIdstringrequire客户端透传的 game_server_id 字段
gameRoleIdstringrequire客户端透传的 game_role_id 字段
gameExtstringrequire客户端透传的 game_ext 字段

通知内容示例 :

{
"appId": 1111,
"attach": {
"gameExt": "ext",
"gameRoleId": "roleID",
"gameServerId": "serviIdext"
},
"channel": 1,
"currency": "CNY",
"notifyId": 264425617725165568,
"notifyTime": 1630915980056,
"outTrxNo": "79867912673",
"paymentType": 0,
"platform": 1,
"products": [
{
"productCode": "com.xd.sdkdemo1.stone30",
"quantity": 1,
"channelSkuCode":"com.tds.sdkdemopro.fxqusd299"
}
],
"status": 1,
"totalAmount": 3.99,
"trxType": 0,
"trxNo": 263336436030607360,
"userId": "262966214111019008"
}

退款通知

目前 Apple Pay 和 Google Pay 支持退款通知,后继会逐渐支持更多支付渠道的退款。如何测试退款请参考 常见问题:如何测试退款

通知内容主体

备注

和支付成功通知内容略有不同。

nameDateTypeOptionsDescription
notifyIdnumberrequire通知唯一 id
appIdnumberrequire商户应用 id
notifyTimenumberrequire通知创建时间戳(毫秒)
userIdstringrequire用户 id
trxNonumberrequire平台交易单号
originalTrxNonumberrequire原始平台交易单号
trxTypenumberrequire交易类型,0: 支付成功,2: 退款
platformnumberrequire平台
channelnumberrequire支付渠道
paymentTypenumberrequire支付方式
productsarrayrequire购买的商品列表,详细见下面解释
currencynumberrequire货币
totalAmountdecimalrequire订单总金额
statusnumberrequire订单状态
successTimenumberrequire退款完成时间戳(毫秒)
attachobjectnullable附加数据,详细见下面解释
警告

trxType 为交易类型,0: 支付成功,2: 退款,请注意区分莫要出现把退款当成支付成功的情况。

trxNo 和 originalTrxNo 是不同的(即:退款订单和支付订单的 ID 是不同的) 游戏可以通过 originalTrxNo 字段来识别原始的支付订单

补款订单再次支付成功不会再收到服务端的到账通知

商品信息

主体内容中的 products 字段,该字段为数组。

nameDateTypeOptionsDescription
productCodestringrequire商品码
quantitynumberrequire数量
channelSkuCodestringrequire支付渠道商品码。只有 Google Pay、Apple Pay 该字段才有值

附加数据

主体内容中的 attach 字段,退款通知内的附加内容与原始支付订单内的附加内容一致。详细字段如下 :

nameDateTypeOptionsDescription
gameServerIdstringrequire客户端透传的 game_server_id 字段
gameRoleIdstringrequire客户端透传的 game_role_id 字段
gameExtstringrequire客户端透传的 game_ext 字段

通知内容示例 :

{
"appId": 1111,
"attach": {
"gameExt": "ext",
"gameRoleId": "roleID",
"gameServerId": "serviIdext"
},
"channel": 1,
"currency": "CNY",
"notifyId": 264425617725165568,
"notifyTime": 1630915980056,
"paymentType": 0,
"platform": 1,
"products": [
{
"productCode": "com.xd.sdkdemo1.stone30",
"quantity": 1,
"channelSkuCode":"com.tds.sdkdemopro.fxqusd299"
}
],
"status": 1,
"totalAmount": 3.99,
"trxNo": 263336438097889345,
"trxType": 2,
"originalTrxNo": 263336436030607360,
"userId": "262966214111019008"
}

通知应答

支付通知 http 应答码为 200204 才会当作正常接收,当回调处理异常时,应答的 HTTP 状态码应为 500,或者 4xx

当商户后台应答失败时,平台将记录下应答的报文,商户应按照以下格式返回:

{  
"code": "SUCCESS",
"msg": "成功"
}

多回调地址

使用场景

当游戏只申请了一个 ClienID,但是游戏服务器有开发服、提审服、正式服等区分时,为了让回调信息能够通知到不同的游戏服务端,游戏可以通过配置 serverId 与对应回调地址来实现这个需求。

配置参数需要在申请开通支付时添加到申请工单内。

配置示例

{
"default":"https://pay.demo.xd.com/callback",
"prod":"https://pay.demo.xd.com/callback",
"stg":"https://pay-stg.demo.xd.com/callback",
"test":"https://pay-test.demo.xd.com/callback"
}

配置中的 key 即为客户端下单参数 serverId:

客户端接口 XD Server 在做支付结果通知时会通过 serverId 查找对应的回调地址,如果查询不到则使用 key 为 default 的配置,默认使用default。

游戏角色信息查询

接口说明

该接口用于网页端支付,用于类似下图的用户充值到账角色确认。

示例

查询 URL 该链接由游戏服务端提供,由平台研发配置到平台的后台(可在开通支付的申请邮件或 Jira 单子中一并提供,或者在 Slack 公开频道#taptap-tds 提供给平台研发)

信息

调用角色查询接口的时机

  • 游戏内打开支付网页后,支付网页会主动查询一次当前玩家的角色 id,如果查询失败或查询接口未返回正确的平台用户 id (即 xdid)会导致玩家无法继续支付流程。
  • 官网网页支付页面玩家可以自行输入角色 id,玩家输入的角色 id 可以通过查询接口查询到平台用户 id 后,玩家才可以继续支付流程。
  • 玩家下单时,SDK 服务端会通过该接口再次验证角色 id,接口失败默认做一次重试,最终查询失败会导致玩家下单失败。

请求参数

GET 方法访问游戏提供的通知 url。

nameDateTypeOptionsDescription
roleIdstringrequire角色 id
serverIdstringrequire服务器 id

返回数据

平台请求之后,游戏的服务返回字段如下:

nameDateTypeOptionsDescription
userIdstringrequire平台用户 id
roleIdstringrequire角色 id
namestringrequire角色昵称(游戏希望展示给玩家什么昵称就返回什么昵称)
avatarstringrequire角色头像
roleLvnumbernullable角色等级
serverIdstringnullable服务器 id
serverNamestringnullable服务器名称

http 响应 status code 应为 200

请求示例

curl -v '{host}/test/v1/game/role?roleId=339064846605987840&serverId=223'

返回示例

{
"userId": "63909809",
"roleId": "1111",
"name": "lvu",
"roleLv": 11,
"avatar":"https://img3.tapimg.com/default_avatars/9cc5d5bcd37bdc024fd3bea3bc58649b.jpg"
}

游戏角色列表查询

该接口用于纯官网页支付,用于查询当前 xdid 的所有游戏角色列表。

特别是在中国大陆开启官网页支付,出于防沉迷政策的要求会需要玩家在网页上登录。此时充值玩家选择充值到该 xdid 的哪个角色上。

示例

查询 URL 该链接由游戏服务端提供,由平台研发配置到平台的后台(可在开通支付的申请 Jira 单子中一并提供)

信息

接口调用时机

  • 国内官网网页支付页面玩家选择了游戏服务器列表之后(如果有的话),会用玩家选择的服务器(serverId)去查询当前登录账号的游戏角色列表。

请求参数

GET 方法访问游戏提供的 url。

nameDateTypeOptionsDescription
userIdstringrequireXDSDK 生成的用户 ID(也就是 xdid)
serverIdstringnullable服务器 id(玩家在游戏服务器列表中选择的服务器 id(如果有的话))

返回数据

平台请求之后,游戏的服务需要当前 xdid 对应的所有可供玩家选择的角色列表信息,results 数组内的字段包括:

nameDateTypeOptionsDescription
roleIdstringrequire角色 id
namestringrequire角色昵称(游戏希望展示给玩家什么昵称就返回什么昵称)
avatarstringrequire角色头像
roleLvnumbernullable角色等级
serverIdstringrequire游戏所在服务器,比如 t_dailay_test/release
serverNamestringnullable服务器名称

http 响应 status code 应为 200

请求示例

curl -v '{host}/test/v1/game/roles?userId=339064846605987840&serverId=223'

返回示例

有游戏角色

HTTP Status Code: 200

{
"code":200,
"msg":"OK",
"detail":"OK",
"results":[
{
"roleId":"1111",
"name":"lvu",
"roleLv":11,
"avatar":"https://img3.tapimg.com/default_avatars/9cc5d5bcd37bdc024fd3bea3bc58649b.jpg"
},
{
"roleId":"2222",
"name":"roll",
"roleLv":3,
"avatar":"https://img3.tapimg.com/default_avatars/9cc5d5bcd37bdc024fd3bea3bc58649b.jpg"
}
]
}

msg 字段为玩家侧信息,detail 字段为开发者信息。 HTTP Status Code 为非 200 时把 msg 字段展示给玩家。

无游戏角色

比如该 xdid 不存在游戏角色 HTTP Status Code: 401

{
"code":401,
"msg":"您所登录账号不存在火炬之光的游戏角色,请先往游戏客户端内创建",
"detail":"该 xdid 非法,不存在游戏角色",
"results":[

]
}

HTTP Status Code 为非 200 时把 msg 字段展示给玩家。

下单前校验

该接口用于游戏官网支付页的下单前校验,用于类似下图在官网充值页下单时调用游戏服务端接口给出提示。

新增 quantity 字段,用于批量购买限购商品时,对于玩家购买是否超限的判断,比如限购2次的商品,玩家批量购买3次,这时会把数量通过 quantity 的字段传给游戏,游戏用来判断。

线上已提供该接口的游戏并且已经开通了批量的游戏需要检查新增 quantity 对于游戏接口是否有影响。

未开通批量的游戏如果需要对限购商品支持批量购买,需要对该接口的 quantity 字段进行处理判断。

开通批量需联系平台 @刘方兴

比如购买数量限制:

限购

比如在线状态校验: 在线状态

该接口由游戏服务端提供,由平台研发配置到后台(可在开通支付的申请邮件或 Jira 单子中一并提供接口地址和 ClientID)。

危险
  • 该方式无法实现真正的限购,只是在下单前和游戏服务端做一次简单确认。玩家依然可以多开浏览器窗口下单,游戏的服务端在到账的时候可能会拦截但是依然会出现其中一笔到账,另一笔不到账(玩家成功下单了)的情况导致客诉。
  • 调用校验接口的时机:玩家下单时,XDSDK 服务端会通过该接口验证是否允许下单,接口失败默认做一次重试,最终查询失败会导致玩家下单失败。

接口说明

请求头

namevalue
Content-Typeapplication/json

请求参数

POST 方法访问游戏提供的通知 url。

nameDateTypeOptionsDescription
roleIdstringrequire角色 id
serverIdstringrequire服务器 id
productSkuCodestringrequire商品码
quantityintrequire购买的商品数量
extrasstringnullable游戏下单时自定义字段

返回数据

XDSDK 服务端请求之后,如果允许购买则可以:

  • http 响应 status code 应为 200
  • 当 http 响应 status code 非 200 时,游戏服务应返回字段如下:
nameDateTypeOptionsDescription
codenumberrequire错误码,用于前端做多语言
msgstringnullable给玩家提示的信息
detailstringrequire开发者信息,便于排查问题

code 游戏服务端可以自定义,但需要把 code 对应的多语言文案给到 XDSDK 的前端研发。 如果 code 未同步给 XDSDK 的前端,那么前端会直接展示游戏限购接口返回体内的 msg 信息。

我们建议游戏服务端直接使用 XDSDK 已经内置的错误码,具体详情请参考下文的内置错误码

危险
  • 当响应体中未包含 code 字段,XDSDK 服务端会把当前下单阻拦并报错,且无法提醒用户无法下单原因,请务必返回code 字段。
  • 当前下单不需要拦截,http 响应 status code 200 即可,否则用户将无法下单。

请求示例

curl --location 'https://xd.cn/order/check' \
--header 'Content-Type: application/json' \
--data '{
"roleId":"12323",
"serverId":"cn-release",
"productSkuCode":"com.xd.sdkdemo1.stone30"
"quantity":1
}'

返回示例

当前下单需要拦截,http 响应 status code 非 200

{
"code": 102,
"msg": "purchase overlimit",
"detail": "当前玩家已购买过该商品"
}

多语言

XDSDK 的前端会根据 code 字段进行多语言适配。

  • 如果使用的是内置错误码,项目组无需关心多语言文案。
  • 如果是自由定义错误码,多语言文案由项目组自行翻译。

内置错误码

我们提前准备好了一份错误码,游戏服务端可以根据游戏商品限购规则返回以下 code,例如玩家重复购买月卡类商品时,code 可以传入 105。

coda中文文案
101请输入正确的角色 ID
102服务器错误,请稍后重试
103当前商品不存在
104订单提交失败,请先保持游戏在线状态
105订单提交失败,你当前商品的购买数量已达到上限
106当前有一笔交易正在进行中,请数分钟后重试!
107服务器错误,请稍后重试
112当前角色不满足购买条件
113当前有一笔交易正在进行中,请1分钟后重试!
114当前有一笔交易正在进行中,请2分钟后重试!
115当前有一笔交易正在进行中,请3分钟后重试!

自定义错误码

内置错误码 code 都不能满足项目组需求时,可以自定义错误码

  • 自定义错误码不能与上面的内置 code 重复
  • 自由定义错误码文案,项目组需要自行翻译多语言版本文案
  • 新增 code 可以在 slack 上 #xd-platform 频道发起需求并 @项管@产品经理

待补款订单查询

该接口由 XD Server 提供。可以通过该接口查询到玩家当前是否存在待补款的订单。

待补款订单:指玩家针对已经发放道具的订单,自己在 Apple Store / Google Play 发起的退款的订单。此类退款订单因为道具已经发放所以可以要求玩家补缴已退款的金额,因此叫待补款订单。

使用场景

当玩家在成功退款后,平台会记录下退款信息。当玩家完成登录后,游戏客户端可以通过 XDSDK 提供的补款查询接口查询到当前待补款订单,此时可以对玩家登录进行拦截。 为了防止客户端补款查询结果被恶意篡改,游戏服务端在验证 token 后也可以再通过该接口查询是否存在待补款订单,并根据查询结果进行拦截。

当玩家在客户端完成补款后,待补款单状态会转为已补款,此时该接口也不再返回该笔订单。服务端可以通过待补款订单是否仍存在判断是否已完成补款。

我们更建议对退款订单进行倒扣(见上文退款通知部分),不建议直接拦截玩家登录。游戏可以根据自身商品特点自行选择合适的方案。

信息

仅可以查询到 Apple Store 或 Google Play 的退款单,该接口不会返回其它渠道的退款单。

当用户完成补款后,该接口不再返回待补款订单,所以该接口不能用来拉取用户历史退款订单流水。

请求地址

  • 海外域名:https://xdsdk-intnl-6.xd.com
  • 国内域名:https://xdsdk-6.xd.cn

REST API 请求的 Base URL(下文 curl 示例中用 {{host}} 表示)。

URLMETHOD功能
/order/v1/user/arrearsGET获取用户当前待补款订单列表

请求方式

请求参数

nameDateTypeOptionsDescription
clientIdstringrequireXD Client ID

请求头

nameDateTypeOptionsDescription
Authorizationstringrequire签名

Authorization 字段的签算过程见 Mac Token 签算 小节。

请求示例

curl --location 'https://{{host}}/order/v1/user/arrears?clientId=d4bjgwom9zk84wk' \
--header 'Authorization: MAC id="HlRLEwCmDk5v9G3cxVaZJ18Fj49gEXHL2IZIM-_T4EK9UxwN1wsyfEEgaESaSDIS1HxS_qAXauYCppmjZ6rmNlanLPmlGZvr4R09jkmBsCNFTbSkzFuMi_ukIzK6ZcBVZCmsLYZ8WJWcBbHtWbW87jjMUpxQSuGIC51unaW1fT0",ts="1681203136",nonce="gPQVk",mac="b1jGKWdy68Ml744Bb8sPiGy/8xs="'

返回内容(JSON)

nameDateTypeOptionsDescription
tradeNonumbernon-nullable平台退款订单号
productIdstringnon-nullable商品 SKU Id
currencystringnon-nullable货币单位
outTradeNostringnon-nullable外部订单号(非游戏单号)
bankTradeNostringnullable支付渠道订单号
refundAmountnumbernon-nullable退款金额
channelIdnumbernon-nullable渠道ID
channelTypenumbernon-nullable渠道类型,具体见下方支付渠道枚举
supplyStatusnumbernon-nullable补款状态 1:待补款
platformnumbernon-nullable平台,具体见下方平台类型枚举

返回示例

{
"code": 200,
"msg": "ok",
"detail": "",
"data": {
"list": [
{
"tradeNo": 344625817118412801,
"productId": "cn.recharge.coin14.99",
"currency": "USD",
"outTradeNo": "344625817122607105",
"bankTradeNo": "",
"refundAmount": 14.990,
"channelId": 1,
"channelType": 1,
"supplyStatus": 1,
"platform": 1
},
{
"tradeNo": 475344677177233408,
"productId": "com.xd.sdkdemo1.stone980",
"currency": "CNY",
"outTradeNo": "475344677177233409",
"bankTradeNo": "",
"refundAmount": 108.000,
"channelId": 1,
"channelType": 1,
"supplyStatus": 1,
"platform": 1
}
]
}
}

游戏内消费通知

为了支持游戏和 TapTap 联合营销活动,游戏内购买指定道具,TapTap赠送月卡,游戏把购买事件通知到平台,平台转发给 TapTap。

  • 海外域名:https://xdsdk-intnl-6.xd.com
  • 国内域名:https://xdsdk-6.xd.cn

REST API 请求的 Base URL(下文 curl 示例中用 {{host}} 表示)。

URLMETHOD功能
/order/v1/game/pay/notifyPOST游戏内消费通知

请求方式

请求参数

nameDateTypeOptionsDescription
userIdstringrequire用户ID
roleIdstringrequire游戏角色ID
serverIdstringrequire游戏服务器ID
productCodestringrequire商品码
appIdnumberrequire商户应用 id
noncestringrequire随机字符串
timestampnumberrequire时间戳
signstringrequire签名

sign 字段的签算过程见 s2s md5 加密 小节。

返回数据

http code 返回200 即为成功。

请求示例

curl --location 'http://127.0.0.1:8080/order/v1/game/pay/notify' \ --data '{ "userId": "1111", "roleId": "1111", "serverId": "111", "productCode": "1111", "appId": 1010, "nonce": "111", "timestamp": 1714474338, "sign": "5522ha6sc071vaxxn39p3fxco67v83g7" }''

返回示例

{ "code": 200, "msg": "ok", "detail": "", "data": true }

安全机制

上述的 支付结果服务端回调游戏角色信息查询限购校验 XDSDK 都提供了如下安全机制。

白名单

如果您的游戏回调地址设置了防火墙,可以根据 服务端出口 ip 文档 获取平台的出口 ip,增加白名单。

验签

为了保证数据安全,我们提供了签名机制。为了避免多次开发,和账户注销的回调通知验签机制保持一致。如果您的游戏已经接入过账户注销的回调通知,那账户和支付的公钥是一样的。如果没有则联系我们提供。

虽然防火墙白名单起到了一定的作用,并且不对内容验签功能也能完成,但是我们还强烈建议游戏对回调内容验签以避免安全漏洞。

具体验签过程参考 服务端回调验签机制

s2s md5 加密

  1. 对所有请求参数按字典顺序排序
  2. 把请求参数按 key1=value1&key2=value2...&key10=value10 的格式拼接
  3. 把秘钥拼接在上一步生成的字符串后(秘钥和平台约定)
  4. 对上一步生成的字符串计算md5

算法示例(php):

ksort($params);
$sign = md5($params . $appKey)

附录

trxType-交易类型枚举

codedescription
0支付
1补单
2退款
备注

目前仅通知了「支付」和「退款」类型的交易结果,但类型以后可能会扩展。

platform-平台类型枚举

codedescription
1iOS
2Android
3Web
4macOS
5Windows
7Unknown

paymentType-支付方式枚举

codedescription
0APP 支付
1移动 WAP 支付
2JSAPI
3扫码支付

status-订单状态枚举

codedescription
0交易成功
1已创建
2待支付
3交易失败
4已取消

channel-支付渠道枚举

codedescription
1APPLE_PAY
2GOOGLE_PAY
3WECHAT_PAY
4ALI_PAY
5PAYPAL
6TOSS
7CODA
8CODA_SHOP
9RAZER
10SMILE_ONE
11UNIPIN
12UNIPIN_SHOP
13PING_PLUS
14MY_CARD
15INTL_ALI_PAY
16ONE_PAY
17STEAM_PAY
信息

目前仅在「交易成功」后发送通知。channel 类型可能会逐渐增多,建议尽量游戏不要对 channel 做特殊判断避免新增了支付渠道无法使用。

currency-标准货币代码

请参考 ISO 代码