# 回调交易结果

# 回调接口验签

验签目的

API 请求在通过公网传输过程中,有被中间人篡改的风险。为确保回调数据的完整性与可信性,平台支持并强烈建议商户在接收回调时进行签名验签

设置方式

登录【收银台后台】→【开发者中心】→【回调地址】→ 添加/编辑。

验签步骤

验签逻辑与接口请求签名大体一致,区别在于数据来源为接收到的回调内容

  1. 获取签名

从 HTTP 请求 Header 中读取签名字段:

sign: {平台生成的签名字符串}
  1. 获取回调参数体

将回调 Body 中的 JSON 参数以 key-value 形式存入一个 Map(字典)结构中。

  1. 添加公共参数

从 Header 中再取出以下字段,并一并加入 Map 中参与验签:

  • access_key
  • timestamp
  • nonce
  1. 构造待签名字符串

将 Map 中的所有 key 按照 ASCII 字典序从小到大排序,并拼接为如下格式的字符串:

key1=value1&key2=value2&...&keyN=valueN
  1. 执行签名计算

使用商户后台绑定的 secret_key 对上述字符串进行以下处理:

  • 使用 HMAC_SHA1 算法加密
  • 将结果进行 Base64 编码,得到本地 sign
  1. 比对签名

将本地生成的 sign 与 Header 中平台传来的 sign 进行比对:

  • ✅ 一致 → 验签通过,可处理业务逻辑
  • ❌ 不一致 → 拒绝处理,建议记录日志以供排查

# 兑换回调

当兑换订单进入终态(如成功、失败)后,平台将向商户预设的 notifyUrl 发送如下回调数据。

回调数据示例

{
  "currencyType":"INR",
  "orderId":"OCURREXCH202505080800451746691245254HAMBIT-U0000000201298031",
  "tokenAmount":"1.193602291716400095",
  "currencyAmount":"100",
  "orderFee":"0.014084507042253522",
  "remark":"test",
  "chainType":"BSC",
  "externalOrderId":"20250508160039180270",
  "orderEntryAmount":"1.179517784674146573",
  "addressTo":"0xa8666442fA7583F783a169CC9F5449ec660295E8",
  "orderCompleteTime":1746691310000,
  "orderAmount":"100",
  "exchangeRate":"83.78",
  "notifyUrl":"https://tofficeapi.hambit.co/api/v1/hambit/hambit-api/test/testNotifySuccess",
  "tokenType":"USDT",
  "exSymbolType":602
}

回调参数说明

参数名 类型 说明
currencyType String 法币类型 BRL,INR
orderId String 订单ID
tokenAmount String 代币数量
currencyAmount String 法币金额
orderFee String 交易手续费(手续费将从结算金额中扣除)
remark String 订单备注
chainType String 区块链类型
externalOrderId String 商户订单ID
orderEntryAmount String 实际收到金额(实际收到金额=换算将收到金额-手续费)
addressTo String 收款地址
orderCompleteTime int 订单完成时间
orderAmount String 订单金额
exchangeRate String 汇率
notifyUrl String 回调URL
tokenType String 代币类型
exSymbolType int 交易类型(601 表示加密货币转法币,602 表示法币转加密货币)

# 回调响应

说明

  • 所有回调均包含签名字段,建议商户务必对回调进行验签,确保回调内容未被篡改。
  • 商户在收到回调数据并处理完成后,需以 JSON格式 响应网关如下数据:

示例响应(成功)

{
  "code": 200,
  "success": true
}

回调补发机制说明(重要)🔥

为确保回调通知的稳定送达与业务一致性,平台设计了多次重试策略。当商户系统未能成功响应回调时(如网络超时、返回非200状态码等),系统将按以下规则进行回调补发:

回调重试节奏(共 4 次):

尝试次数 间隔时间(约) 说明
第 1 次 约 2 分钟后 首次失败后触发第一次重试
第 2 次 约 2 分钟后 第一次重试失败后触发第二次重试
第 3 次 再约 11分钟后 第二次重试失败后再次重试
第 4 次 再约 2分钟后 第三次重试失败后进入下一次重试

注意:以上间隔时间为系统内部调度间隔,商户后台所记录的“回调时间”包含了商户处理/响应时间,因此显示上可能与实际推送时间存在 1 分钟左右误差。

实际情况提醒

  • 当线上订单量较大时,回调可能存在队列延迟,请确保服务端支持高并发处理能力;
  • 每次回调均为幂等操作,建议商户侧务必支持幂等判断;
  • 最多 4 次重试推送仍失败后,则不再自动重试,建议通过后台手动触发回调。

回调响应参数

Param Type Required Description
code int 状态码,成功为 200
success boolean 响应是否成功

# 回调通知 URL 配置

支持两种通知地址配置方式:

  1. 【商户后台】配置统一回调地址
  • 可在「商户后台」→「开发者中心」中配置。
  • 适用于大部分订单共用的回调处理逻辑。

img

2.订单级别手动指定回调地址(notifyUrl)

  • 在创建订单接口中可传 notifyUrl 字段。
  • 若订单中指定了 notifyUrl 参数,则系统将仅使用该地址作为回调通知目标地址

地址优先级说明

订单中的 notifyUrl 优先级高于统一配置的回调地址。

响应状态码优先级说明

平台以 HTTP 响应状态码 (**status_code**) 是否为 200 作为通知是否成功的唯一判断标准

具体规则如下:

  • 只要商户系统返回 HTTP 200**,平台即认为回调成功**
    • 此时即使返回内容不是 { "code": 200, "success": true } 也会被忽略。
  • ❌ 如果返回 status_code ≠ 200(如 400/500)或无响应,则判定为失败,平台将自动进行重试推送。