【问题标题】:OAuth unsupported_grant_typeOAuth unsupported_grant_type
【发布时间】:2016-09-03 20:57:12
【问题描述】:

我正在尝试通过 curl 将 OAuth 代码与授权令牌交换。服务器 API 文档说,我应该发送 POST 数据,并且我正在这样做:

$ch = curl_init();

curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);    // return result
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0);    // disallow redirection
curl_setopt($ch, CURLOPT_TIMEOUT, 5);           // timeout 5s
curl_setopt($ch, CURLOPT_URL, $url);            // OAuth access token url
curl_setopt($ch, CURLOPT_POST, 1);              // send via POST

// I have prepared query arguments as an array $args
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($args));

// Turning on some debug info
curl_setopt($ch, CURLINFO_HEADER_OUT, 1);

// Executing curl
$data = curl_exec($ch);

问题在于服务器响应。我总是收到 OAuth 错误:unsupported_grant_type。所有文档来源都说参数 grant_type 必须设置为“authorization_code”值(在此 OAuth 步骤的所有情况下),但无论如何它都不起作用。有什么想法吗?

【问题讨论】:

    标签: php post curl oauth


    【解决方案1】:

    这是针对 SalesForce OAuth 的吗?

    如果是这样,他们需要设置 Content-Type 和 Content-Length,例如:

    curl_setopt($ch, CURLOPT_HTTPHEADER, array("Content-type: application/x-www-form-urlencoded", "Content-length: ".strlen($params)));
    

    【讨论】:

      【解决方案2】:

      由于(根据评论)http_build_query($args) 返回一个数组,curl 正在发送内容类型为multipart/form-data 的 POST(参见docs for curl_setopt)。 OAuth 服务器可能需要application/x-www-form-urlencoded,在这种情况下http_build_query 需要返回一个像para1=val1&para2=val2&... 这样的urlencoded 字符串。

      【讨论】:

      • http_build_query($args) 只能返回一个字符串;它接收数组。该功能不是为了做其他事情而构建的。 [http_build_query (混合 $query_data [, string $numeric_prefix [, string $arg_separator [, int $enc_type = PHP_QUERY_RFC1738 ]]] ) : string](php.net/manual/en/function.http-build-query.php)
      【解决方案3】:

      您的通用 CURL 请求应使用自定义

      1. 表单数据参数/查询参数,
      2. 内容类型

      【讨论】:

        【解决方案4】:

        以下是使用来自谷歌服务器的 client_和 client_secret 返回身份验证令牌的工作代码。

        `tok_url:OAuth Token url, Auth_token: authentication token returned from google servers when cust_id and cust_secret are passed`
        
        int get_refresh_token(char* tok_url,char* auth_token,char*cust_id,char*cust_secret)
        {
            CURL *curl;
          CURLcode res;
            char data[1024]="\0";
            strcat(data,"code=");
            strcat(data,auth_token);
            strcat(data,"&client_id=");
            strcat(data,cust_id);
            strcat(data,"&client_secret=");
            strcat(data,cust_secret);
            strcat(data,"&redirect_uri=");
            strcat(data,"urn:ietf:wg:oauth:2.0:oob");
            strcat(data,"&grant_type=authorization_code");
            puts(data);
        
        
          /* In windows, this will init the winsock stuff */ 
          curl_global_init(CURL_GLOBAL_ALL);
        
          /* get a curl handle */ 
          curl = curl_easy_init();
          if(curl) {
            /* First set the URL that is about to receive our POST. This URL can
               just as well be a https:// URL if that is what should receive the
               data. */ 
            curl_easy_setopt(curl, CURLOPT_URL, tok_url);
            /* Now specify the POST data */ 
            curl_easy_setopt(curl, CURLOPT_POSTFIELDS, data);
        
            /* Perform the request, res will get the return code */ 
            res = curl_easy_perform(curl);
            /* Check for errors */ 
            if(res != CURLE_OK)
              fprintf(stderr, "curl_easy_perform() failed: %s\n",
                      curl_easy_strerror(res));
        
            /* always cleanup */ 
            curl_easy_cleanup(curl);
          }
          curl_global_cleanup();
        }
        

        【讨论】:

          猜你喜欢
          • 2019-04-22
          • 2021-10-02
          • 1970-01-01
          • 2020-06-26
          • 1970-01-01
          • 1970-01-01
          • 2017-08-29
          • 1970-01-01
          • 2020-09-08
          相关资源
          最近更新 更多