You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

生成E-Trade API的HMAC-SHA1签名时遇invalid_signature错误求助

解决E-Trade API请求令牌签名无效问题

你的代码存在几个关键问题导致签名无效,以下是问题分析和修正方案:

问题1:签名密钥缺少必需的末尾&

OAuth 1.0a规定,请求令牌(request_token)阶段的签名密钥格式为:rawurlencode(consumerSecret) + "&"。即使此时还没有获取到oauth令牌密钥(oauthTokenSecret),末尾的&也必须保留,这是很多开发者容易忽略的细节。你的代码仅使用了rawurlencode($consumerSecret),缺少了这个&。

问题2:OAuth参数的键未进行URL编码

OAuth要求所有参数的键和值都必须单独进行URL编码(rawurlencode),你的代码只对参数值做了编码,参数键(如oauth_consumer_key)直接使用原始字符串,不符合规范。

问题3:基字符串参数拼接需确保严格字典序

虽然你当前的参数顺序刚好符合字典序,但为了鲁棒性,建议显式排序参数,避免后续添加参数时出错。


修正后的代码

public function generateSignature($request, $timestamp, $nonce, $signatureMethod, $version, $consumerKey, $consumerSecret)
{
    // 整理所有OAuth参数,键值对都编码,然后按字典序排序
    $oauthParams = [
        rawurlencode('oauth_consumer_key') => rawurlencode($consumerKey),
        rawurlencode('oauth_nonce') => rawurlencode($nonce),
        rawurlencode('oauth_signature_method') => rawurlencode($signatureMethod),
        rawurlencode('oauth_timestamp') => rawurlencode($timestamp),
        rawurlencode('oauth_version') => rawurlencode($version)
    ];
    ksort($oauthParams); // 按键的字典序排序

    // 拼接参数为"key=value&key=value"格式
    $paramString = http_build_query($oauthParams, '', '&');

    // 构建签名基字符串
    $base = $request['method'] . "&" 
          . rawurlencode($request['url']) . "&" 
          . rawurlencode($paramString);

    // 构建签名密钥:consumerSecret编码后加&(即使无tokenSecret)
    $key = rawurlencode($consumerSecret) . "&";

    // 生成HMAC-SHA1签名并base64编码
    $signature = base64_encode(hash_hmac('sha1', $base, $key, true));

    return $signature;
}

验证要点

  1. 确保$request['method']是大写的(如GET或POST),OAuth要求请求方法必须大写。
  2. 确认$request['url']是不带查询参数的基础URL(E-Trade的request_token接口是https://api.etrade.com/oauth/request_token,无查询参数,这部分没问题)。
  3. 检查timestamp和nonce是否与请求头中携带的完全一致,这两个参数必须实时生成且唯一。

内容的提问来源于stack exchange,提问作者bufferking

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.12 15:52:34