一般来说,在 URL 中只需要用户名密码是个坏主意。即使您使用 SSL,URL 及其所有查询参数也不安全。如果您希望您的提要是安全的,您可以使用诸如 HMAC-SHA1 或 HMAC-SHA256 之类的散列方法使用私钥对您的请求进行签名。它的工作原理是这样的。
客户端需要两个密钥,公钥和私钥
PublicKey: ABCDJJJZ7BW9P0IH2NI3
PrivateKey: uFehWXvcM7mf==c8ZhOe3Fz+6d+zyQ2ja4A3De1N
从动词、url、标题和正文构建一个字符串。建议您使用 SSL 或在 url 中包含 Expire 参数,以防止任何黑客有效地执行重放攻击。确保日期和主机包含在标题中,日期对于确保签名始终在变化非常重要。
verb + \n
url + \n
header1: value + \n
header2: value + \n
body
然后客户端使用上述哈希方法对请求进行签名。伪代码看起来像这样。
base64encode(hmac-sha1($private_key, $string_to_sign))
a 标头附加到包含签名和公钥的请求中
Authorization: $public_key:$signature
当服务器收到消息时,他们使用标头中收到的公钥为用户检索私钥Authorization
。然后服务器执行相同的算法,如果两个签名匹配,则服务器知道请求已通过身份验证,因为只有具有正确公钥和私钥的客户端才能生成相同的签名。
这是使用此算法签署请求的 PHP 代码片段。
public function sign() {
$time = time();
$date = gmdate(self::DATE_FORMAT_RFC2616, $time);
$verb = $this->payload['verb'];
$headers = $this->payload['headers'];
$query = $this->payload['query'];
$body = $this->payload['body'];
// Build the content string
$endpoint = $this->endpoint;
// Set the expiration time of the request
if($this->expires != 0 && !isset($query['Expires'])) {
$query['Expires'] = $time + ($this->expires * 60);
}
// Add the date to the request headers
$headers['date'] = $date;
// Add the host to the request headers
$headers['host'] = $this->host;
// Sort the query array and convert to querystring
uksort($query, 'strnatcasecmp');
$querystring = SUUtilities::to_query_string($query);
// Sort the headers to be sure they're in the right order
$modified_headers = array();
uksort($headers, 'strnatcasecmp');
// Concatinate the headers so the key and value are a single string
$include = array('date', 'host');
foreach($headers as $key => $value) {
if(in_array($key, $include) || substr($key, 0, 5) == "x-sbr") {
$modified_headers[] = preg_replace('/\s/', '', strtolower($key)).": ".$value;
}
}
// Build the string to sign
$string_to_sign = $verb.PHP_EOL
.$endpoint."?".$querystring.PHP_EOL
.implode(PHP_EOL, $modified_headers).PHP_EOL
.$body;
// Create the signature for the request
$signature = base64_encode(hash_hmac('sha1', $string_to_sign, $this->credentials['private_key'], true));
// Add the authorization header to the list of headers.
array_push($modified_headers, 'authorization: SBR '.$this->credentials['key'].':'.$signature);
$request = array();
$request['headers'] = $modified_headers;
$request['host'] = $this->host;
$request['endpoint'] = $endpoint;
$request['query'] = $query;
return $request;
}
其他资源: