跳转到主要内容

Documentation Index

Fetch the complete documentation index at: https://docs.xpaylabs.com/llms.txt

Use this file to discover all available pages before exploring further.

XPayLabs 使用 HMAC-SHA256 请求签名对每个 API 请求进行身份验证。与传统的 Bearer 令牌身份认证不同,XPayLabs 要求每个请求都包含一个基于请求负载计算的加密签名。这确保了请求的完整性并防止重放攻击。

HMAC-SHA256 签名格式

每个 API 请求都包含一个包含四个字段的 ReqPayload 包装:
字段类型描述
signstringdata 对象 JSON 字符串的 HMAC-SHA256 签名
timestampinteger请求创建时的 Unix 时间戳(秒)
noncestring唯一随机字符串,绝不重复使用
dataobject实际的请求负载
sign 字段使用您的商家令牌作为 HMAC 密钥进行计算。

如何计算 HMAC 签名

算法

  1. data 对象序列化为 JSON 字符串(无格式化、无多余空格)。
  2. 计算 HMAC-SHA256(data_json, merchant_token)
  3. 将结果转换为小写十六进制字符串。
  4. 将此值设置为 sign 字段。

Node.js

import crypto from "crypto";

const MERCHANT_TOKEN = process.env.XPAYLABS_MERCHANT_TOKEN;

function signRequest(data) {
  const json = JSON.stringify(data);   // 紧凑 JSON,无多余空格
  return crypto
    .createHmac("sha256", MERCHANT_TOKEN)
    .update(json, "utf8")
    .digest("hex");
}

const request = {
  sign: signRequest({ amount: "100.00", symbol: "USDT", chain: "TRON" }),
  timestamp: Math.floor(Date.now() / 1000),
  nonce: crypto.randomUUID(),
  data: { amount: "100.00", symbol: "USDT", chain: "TRON" },
};

Python

import hmac
import hashlib
import json
import time
import uuid

MERCHANT_TOKEN = "your-merchant-token"

def sign_request(data: dict) -> str:
    json_str = json.dumps(data, separators=(",", ":"))  # 紧凑 JSON
    return hmac.new(
        MERCHANT_TOKEN.encode("utf-8"),
        json_str.encode("utf-8"),
        hashlib.sha256,
    ).hexdigest()

request = {
    "sign": sign_request({"amount": "100.00", "symbol": "USDT", "chain": "TRON"}),
    "timestamp": int(time.time()),
    "nonce": str(uuid.uuid4()),
    "data": {"amount": "100.00", "symbol": "USDT", "chain": "TRON"},
}

Go

package main

import (
    "crypto/hmac"
    "crypto/sha256"
    "encoding/hex"
    "encoding/json"
    "fmt"
    "time"
    "github.com/google/uuid"
)

func signRequest(data interface{}, token string) string {
    jsonBytes, _ := json.Marshal(data)
    mac := hmac.New(sha256.New, []byte(token))
    mac.Write(jsonBytes)
    return hex.EncodeToString(mac.Sum(nil))
}

func main() {
    data := map[string]interface{}{
        "amount":  "100.00",
        "symbol":  "USDT",
        "chain":   "TRON",
    }
    request := map[string]interface{}{
        "sign":      signRequest(data, "your-merchant-token"),
        "timestamp": time.Now().Unix(),
        "nonce":     uuid.New().String(),
        "data":      data,
    }
    fmt.Printf("%+v\n", request)
}
JSON 序列化必须是紧凑格式——键值对之间无空格、无换行。不同的 JSON 序列化库可能产生不同的输出;始终针对一个已知可用的示例测试您的签名计算。

时间戳和 nonce 要求

timestampnonce 字段用于防止重放攻击:
  • 时间戳:您的服务器时钟必须在 XPayLabs 服务器时间的 5 分钟 以内。超过 5 分钟的请求将被拒绝。
  • Nonce:每个请求必须使用唯一的 nonce。XPayLabs 会跟踪已使用的 nonce 并拒绝重复。UUID 或加密随机字符串效果良好。

XPayLabs 如何验证服务器端签名?

XPayLabs 通过使用您存储的商家令牌重新计算 HMAC-SHA256 签名来验证每个请求。如果签名不匹配,或者时间戳超出容差范围,请求将被拒绝并返回 401 Unauthorized 响应。

如何保护您的商家令牌安全

  • 将商家令牌存储在环境变量或密钥管理器中。
  • 切勿在源代码或客户端应用程序中硬编码令牌。
  • 定期轮换令牌并更新配置。
  • 令牌是您的商家服务器与 XPayLabs 网关之间的共享密钥。它不会在 API 请求中通过网络发送。
Last modified on May 31, 2026