API 接口签名验证
更新时间:2023.12.04 09:23:00
API 接口签名验证
API 请求
所有 API 接口均按照如下方式组装请求报文,请求响应参数全部使用string
类型,为空字段使用""
,对象皆为 JSON 格式。
请求方式:post
请求/响应头:
参数名 | 类型 | 必须 | 备注 |
---|---|---|---|
Content-Type | String | 是 | 内容类型,固定值:application/json |
请求body
{
"content":"content_base64",
"sign":"sign",
"appKey":"appKey"
}
字段名 | 类型 | 描述 |
---|---|---|
content | String | 请求参数JSON结构体的base64编码字符串 |
sign | String | content 内容拼接上 merchantSecret 进行md5计算后的签名 |
appKey | String | appkey 参考 获取 appkey |
API响应
请求成功响应body
{
"responseCode":"000000",
"responseMessage":"success",
"content":"content_base64",
"sign":"sign"
}
请求失败响应body
{
"responseCode":"204005",
"responseMessage":"Authentication failed"
}
接口回调返回body
Paynicorn 给到商户的异步通知时使用
{
"content":"content_base64",
"sign":"sign"
}
字段名 | 类型 | 描述 |
---|---|---|
content | String | 响应参数JSON结构体的base64编码字符串 |
sign | String | content 内容拼接上 merchantSecret 进行md5计算后的签名 |
请注意:响应判断逻辑,首先验证签名是否正确,然后解析Base64编码获取content业务响应数据。
请求失败响应码
响应码 | 响应消息 | 描述 |
---|---|---|
000000 | success | 接口调用成功,业务处理详情根据content判断 |
204404 | 404 NOT FOUND | 接口地址不可达 |
204000 | Request is empty | 请求报文为空 |
204002 | App key is empty | 请求AppKey为空 |
204003 | Content is invalid | 请求Content不合法 |
204004 | Sign is invalid | 请求Sign不合法 |
204005 | Authentication failed | 签名验证失败 |
204006 | The number of test requests exceeds the limit | 该支付应用在测试模式下请求次数超限,请登录商户平台进行重置 |
205999 | Unknow Error | 未知失败.如果是支付\提现\退款返回该错误,后续需要根据查询来判断业务的确切状态 |
签名
请求参数使用 base64 编码生成字符串 content_base64 ,再使用 md5 算法对 content_base64 和 merchant secret 的拼接字符串生成签名 sign = md5(content_base64+merchantSecret) 。
数据准备
- appKey:79n7730m4916aT75h0cJ
- merchant secret:143f824b235c4a649b60fae3d1aa5fe6
- 请求接口: https://api.paynicorn.com/trade/v3/transaction/pay
- 请求对象 bizReq:
{
"amount": "30000",
"countryCode": "ID",
"cpFrontPage": "http://www.baidu.com",
"currency": "IDR",
"email": "111@111.com",
"memo": "Memo",
"orderDescription": "I am Test!",
"payMethod": "DANA",
"phone": "02219092345",
"orderId":"TEST1609409844610"
}
编码
- 对请求对象字符串进行Base64编码
content: eyJhbW91bnQiOiIzMDAwMCIsImNvdW50cnlDb2RlIjoiSUQiLCJjcEZyb250UGFnZSI6Imh0dHA6Ly93d3cuYmFpZHUuY29tIiwiY3VycmVuY3kiOiJJRFIiLCJlbWFpbCI6IjExMUAxMTEuY29tIiwibWVtbyI6Ik1lbW8iLCJvcmRlckRlc2NyaXB0aW9uIjoiSSBhbSBUZXN0ISIsInBheVR5cGUiOiJEQU5BIiwicGhvbmUiOiIwMjIxOTA5MjM0NSIsInVzZXJJZCI6IlUyMDMyMzEyMyIsIm9yZGVySWQiOiJYWlNfVEVTVDE2MDk0MDk4NDQ2MTAifQ==
- 示例代码(CryptoJS)
var strBizReq = JSON.stringify(bizReq);
var wordArray = CryptoJS.enc.Utf8.parse(strBizReq);
var base64 = CryptoJS.enc.Base64.stringify(wordArray).toString();
签名
- 对编码步骤中生成的Base64编码字符串拼接上 merchantsecret 进行MD5签名
sign: 3dc08594b8877479d8a5cb44a5b76b21
- 示例代码(CryptoJS)
var merchantSecret = "143f824b235c4a649b60fae3d1aa5fe6";
var signStr = CryptoJS.MD5(base64+merchantSecret).toString();
请求对象组装
- 使用上述步骤中的生成的结果组装请求对象
{
"appKey": "79n7730m4916aT75h0cJ",
"content": "eyJhbW91bnQiOiIzMDAwMCIsImNvdW50cnlDb2RlIjoiSUQiLCJjcEZyb250UGFnZSI6Imh0dHA6Ly93d3cuYmFpZHUuY29tIiwiY3VycmVuY3kiOiJJRFIiLCJlbWFpbCI6IjExMUAxMTEuY29tIiwibWVtbyI6Ik1lbW8iLCJvcmRlckRlc2NyaXB0aW9uIjoiSSBhbSBUZXN0ISIsInBheVR5cGUiOiJEQU5BIiwicGhvbmUiOiIwMjIxOTA5MjM0NSIsInVzZXJJZCI6IlUyMDMyMzEyMyIsIm9yZGVySWQiOiJYWlNfVEVTVDE2MDk0MDk4NDQ2MTAifQ==",
"sign": "3dc08594b8877479d8a5cb44a5b76b21"
}
请求接口
- 返回对象示例
{
"responseCode": "000000",
"responseMessage": "success",
"content": "eyJjb2RlIjoiMDAwMCIsIm1lc3NhZ2UiOiJzdWNjZXNzIiwidHhuSWQiOiIzMjAxMjMxMDAwMDAwMDYwMiIsInN0YXR1cyI6Ii0xIiwid2ViVXJsIjoiaHR0cHM6Ly9oNS12My10ZXN0LnBheW5pY29ybi5jb20vIy9pbmRleD90PUowNVQ2OW0zNzlfMDAwMDAzMTIzMDIxMDAwNjI3bjcwNDFhN2hjJmNwRnJvbnRQYWdlPWh0dHAlM0ElMkYlMkZ3d3cuYmFpZHUuY29tIn0=",
"sign": "f64f37a0210a1ce55be63602369b12b8"
}
验证签名
- 对返回报文中的content进行签名验证
- 示例代码(CryptoJS)
var respSignValid = CryptoJS.MD5(response.json().content + merchantSecret).toString();
console.log("validResult:" + (response.json().sign == respSignValid));
解析报文
- 对返回对象中的content内容进行Base64解析.
{
"code": "0000",
"message": "success",
"txnId": "32012310000000602",
"status": "-1",
"webUrl": "https://h5-v3.paynicorn.com/#/index?t=J05T69m379_000003123021000627n7041a7hc&cpFrontPage=http%3A%2F%2Fwww.baidu.com"
}
本文导读