1

我正在尝试通过 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 步骤的所有情况下),但无论如何它都不起作用。任何想法?

4

4 回答 4

1

这是针对 SalesForce OAuth 的吗?

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

curl_setopt($ch, CURLOPT_HTTPHEADER, array("Content-type: application/x-www-form-urlencoded", "Content-length: ".strlen($params)));
于 2013-03-21T14:42:41.253 回答
0

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

于 2012-08-23T22:45:12.403 回答
0

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

  1. 表单数据参数/查询参数,
  2. 内容类型
于 2015-05-12T02:13:38.697 回答
0

以下是使用来自谷歌服务器的 client_and 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();
}
于 2016-09-03T12:57:12.910 回答