API 请求签名生成规则

编辑于 2022-08-25 16:22:06 阅读 1037

总结一下常见的 签名生成规则

规则1

客户端

每个 HTTP 请求中均需要携带以下的 HTTP 标头字段(HTTP Request Header)

默认名称 带 RC-前缀 类型 说明
App-Key RC-App-Key String 后台分配的 App Key
Nonce RC-Nonce String 随机数,不超过 18 个字符
Timestamp RC-Timestamp String 时间戳,从1970年1月1日0点0分0秒开始到现在的毫秒数
Signature RC-Signature String 数据签名。您需要参考下文的签名计算方法生成该字段的值

签名计算方法

将以下三个字符串按顺序(App Secret + Nonce + Timestamp)拼接成一个字符串,进行 SHA1 哈希计算。

  • App Secret:应用 App Key 所对应的 App Secret。
  • Nonce:随机数
  • Timestamp:时间戳

以下是 PHP 代码示例:

$conf=['abc'=>'defg'];//app_key=>app_secret
//重置随机数种子。
srand((double)microtime()*1000000);
$appsecret = $conf['abc']; // App Secret
$nonce = rand(); // 获取随机数
$timestamp = time()*1000; // 获取时间戳(毫秒)
$header=[
    'RC-App-Key'=>'abc',
    'RC-Nonce'=>$nonce,
    'RC-Timestamp'=>$timestamp,
    'RC-Signature'=>sha1($appsecret.$nonce.$timestamp),
];

服务端

$conf=['abc'=>'defg'];//app_key=>app_secret
$appkey=$this->request->header('RC-App-Key', '', 'str');
$nonce=$this->request->header('RC-Nonce', '', 'str');
$timestamp=$this->request->header('RC-Timestamp', '', 'str');
$signature=$this->request->header('RC-Signature', '', 'str');

$dif =time() - $timestamp/1000;//±一分钟验证
if($dif > 60 || $dif <-60) die('timestamp error');
//验证签名
$appsecret = $conf[$appkey]??''; // App Secret
if (empty($appsecret)) die('appkey error');
if (sha1($appsecret.$nonce.$timestamp)!==$signature) die('signature error');

//删除1分钟前的记录
$time=time();
$this->cache()->zRemRangeByScore('nonces', 0, $time-60);
$r=$this->cache()->zScore('nonces', $nonce);
if (false===$r){
    $r=$this->cache()->zAdd('nonces', $time, $nonce);
    file_put_contents('./log.txt', $time.' - '.date('Y-m-d H:i:s').PHP_EOL, FILE_APPEND);
}else return $this->status(0, '无法重复请求');

规则2

$appkey='abc';//双方约定的key,不参与http请求,只用于计算签名
$sign=112233;//请求带的签名
$params=[
    'timestamp'=>time(),
    'name'=>111,
];
$params['appkey']=$appkey;
ksort($params);//数组key以字典顺序排序
$str='';
foreach ($params as $key=>$value){
    $str.=$value;
}
//生成签名
$sign2=md5($str);

广而告之,我的新作品《语音助手》上架Google Play了,欢迎下载体验