title: 接口验证机制

本篇文档介绍短信接口的验证机制。

短信发送使用数字签名(signature)的验证模式。这种模式能够有效避免签名密钥在传输途中的泄露,是安全级别很高的一种加密验证方式。

数字签名验证模式

调用接口时, 用户不需要把签名密钥 (SMS_KEY) 作为参数明文传输, 而是将数字签名 (signature) 作为参数传输给服务器,服务器端会验证此数字签名 (signature) 的正确性。

生成数字签名的方法

1.将实际调用 API( 发送验证码短信发送通知类短信校验验证码查询发送状态 )的参数以字母升序(A-Z)排列,除去其中的 signature字段。

特别注意以下规则:

  • 参数名以字母升序(A-Z)排列;
  • 传送的参数signature不参与签名。

例如,传送的参数如下:

  1. templateId: 100001
  2. mobile: "['13500000000']"
  3. timestamp:'1492675740231'

2.将参数以字母升序(A-Z)排列,再以 'key=value'+ '&' + 'key=value'的方式连接所有参数,得到字符串 param_str

  1. param_str="mobile=130xxxxxxxx&templateId=100001&timestamp=1492675740231"

3.以 param_str + ‘&’ + SMS_KEY 的方式得到字符串 sign_str

  1. sign_str="mobile=130xxxxxxxx&templateId=100001&timestamp=1492675740231&$SMS_KEY"

SMS_KEY (短信 API 密钥) 在 控制面板-短信-配置 中获取,操作如下:

title: 接口验证机制 - 图1

4.计算 sign_str的 SHA256值 (64位, 不区分大小写), 得到 signature

5.该签名用于各个接口的访问。

Java 示例如下(其他语言规则一致):

  1. // 发送短信验证码
  2. public static void sendCode(String templateId, String mobile) {
  3. long timestamp = System.currentTimeMillis();
  4. Map<String, String> params = new HashMap<String, String>();
  5. // 设置请求参数
  6. params.put("templateId", templateId);
  7. params.put("mobile", mobile);
  8. params.put("timestamp", String.valueOf(timestamp));
  9. // 对以上三个请求参数进行升序排列
  10. Map<String, Object> sortedMap = new TreeMap<String, Object>(new Comparator<String>() {
  11. public int compare(String arg0, String arg1) {
  12. // 忽略大小写
  13. return arg0.compareToIgnoreCase(arg1);
  14. }
  15. });

此处可参考完整 示例代码

提示:

  • 生成数字签名时, 参数不要使用urlencode。在调用 api 时, 才需要对参数做 urlencode
  • &是代码中使用的连接符, +是文档显示之用。