签名与验签
请求加签和回调验签使用同一套 HMAC-MD5。发请求时用您发送的加签字段计算,收到回调后用文档中标为参与签名的字段重算并比较。
签名生成的通用步骤如下:
- 从参数表中选择需要加签的字段,按参数名 ASCII 字典序排序,拼成
key1=value1&key2=value2…得到 stringA。 - 以
appSecret为 HMAC key,对 stringA 做 HMAC-MD5,再将 hex 转为大写,即为signature。密钥只作 HMAC key,不要拼进 stringA。
参数名区分大小写。字段集合以各接口参数表「是否签名 = 是」为准,signature 只承载计算结果。
举例(PHP)
以下按「提交订单」需要加签的字段演示(已按字典序):
$stringA = 'amount=10.99&appId=k-mch8x2k1p4q9&asset=USDT¤cy=USD&merchantOrderNo=ORD-20260822-0001&network=TRC¬ifyUrl=https://merchant.example.com/ucashier/notify';
$appSecret = 'sk-w7Kp2nQm4xR9aB3c';
$signature = strtoupper(hash_hmac('md5', $stringA, $appSecret));
// 07BA8514788F143D2437E0D6F4C028D0举例(Node.js)
const crypto = require('crypto');
const stringA = 'amount=10.99&appId=k-mch8x2k1p4q9&asset=USDT¤cy=USD&merchantOrderNo=ORD-20260822-0001&network=TRC¬ifyUrl=https://merchant.example.com/ucashier/notify';
const appSecret = 'sk-w7Kp2nQm4xR9aB3c';
const signature = crypto.createHmac('md5', appSecret).update(stringA, 'utf8').digest('hex').toUpperCase();举例(Java)
import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
String stringA = "amount=10.99&appId=k-mch8x2k1p4q9&asset=USDT¤cy=USD&merchantOrderNo=ORD-20260822-0001&network=TRC¬ifyUrl=https://merchant.example.com/ucashier/notify";
String appSecret = "sk-w7Kp2nQm4xR9aB3c";
Mac mac = Mac.getInstance("HmacMD5");
mac.init(new SecretKeySpec(appSecret.getBytes(StandardCharsets.UTF_8), "HmacMD5"));
byte[] digest = mac.doFinal(stringA.getBytes(StandardCharsets.UTF_8));
StringBuilder hex = new StringBuilder();
for (byte value : digest) {
hex.append(String.format("%02X", value & 0xFF));
}
String signature = hex.toString();举例(Python)
import hashlib
import hmac
string_a = (
"amount=10.99&appId=k-mch8x2k1p4q9&asset=USDT¤cy=USD&merchantOrderNo=ORD-20260822-0001&network=TRC¬ifyUrl=https://merchant.example.com/ucashier/notify"
)
app_secret = "sk-w7Kp2nQm4xR9aB3c"
signature = hmac.new(app_secret.encode("utf-8"), string_a.encode("utf-8"), hashlib.md5).hexdigest().upper()