为啥我的 twitter oauth 访问令牌无效/过期

Posted

技术标签:

【中文标题】为啥我的 twitter oauth 访问令牌无效/过期【英文标题】:Why is my twitter oauth access token invalid / expired为什么我的 twitter oauth 访问令牌无效/过期 【发布时间】:2013-01-08 06:31:44 【问题描述】:

我正在使用 Twitter 将用户登录到一个网站,在我尝试获取有效的访问令牌之前,该网站似乎正在运行。

require("twitteroauth.php");
require 'twconfig.php';
session_start();

$twitteroauth = new TwitterOAuth(YOUR_CONSUMER_KEY, YOUR_CONSUMER_SECRET);
$request_token = $twitteroauth->getRequestToken('http://****/tw_response.php');

$oauth_token = $request_token['oauth_token'];
$_SESSION['oauth_token'] = $oauth_token;

$oauth_token_secret = $request_token['oauth_token_secret'];
$_SESSION['oauth_token_secret'] = $oauth_token_secret;

if ($twitteroauth->http_code == 200) 
    url = $twitteroauth->getAuthorizeURL($request_token['oauth_token']);
    header('Location: '.$url);
 else 
    die('Something wrong happened.');

这似乎工作正常,将我重定向到 twitter 以登录并确认访问,然后将我返回到 tw_response.php(我的回调 url),在 url 中有以下变量:

http://example.com/login.php?oauth_token=sO3X...yj0k&oauth_verifier=Ip6T...gALQ 

然后我在 tw_response.php 中尝试获取访问令牌,但它报告为无效。我尝试使用var_dump查看访问令牌的内容如下:

require("twitteroauth.php");
require 'twconfig.php';
session_start();

$oauth_verifier = $_REQUEST['oauth_verifier'];
$oauth_token = $_SESSION['oauth_token'];
$oauth_token_secret = $_SESSION['oauth_token_secret'];

$twitteroauth = new TwitterOAuth(YOUR_CONSUMER_KEY, YOUR_CONSUMER_SECRET, $oauth_token, $oauth_token_secret);

$access_token = $twitteroauth->getAccessToken($data['oauth_verifier']);
var_dump($access_token);

var_dump 的结果以“invalid / expired Token”结尾:

array(8) 
    ["oauth_url"] => string(104) ""1.0" encoding="UTF-8"?>/oauth/access_token?oauth_consumer_key=ceE...9Dg"
    ["oauth_nonce"]=> string(32) "c52...d07"
    ["oauth_signature"]=> string(28) "ry7...Fcc="
    ["oauth_signature_method"]=> string(9) "HMAC-SHA1"
    ["oauth_timestamp"]=> string(10) "1359031586"
    ["oauth_token"]=> string(40) "sO3...j0k"
    ["oauth_verifier"]=> string(43) "Ip6...ALQ"
    ["oauth_version"]=> string(63) "1.0 Invalid / expired Token "

【问题讨论】:

这是在使用 Abraham Williams 的库吗?似乎getAccessToken(code) 仅在您调用的页面为用户提供允许访问后输入的代码时才有效。我认为您在使用回调 URL 时需要同时使用这两条信息。 如果您使用有效的回调 URL,则无需使用您的凭据验证 oauth_verifier。无论如何都要检查一下。 你的服务器时钟运行正常吗? 我觉得这个链接可以帮到你phpgang.com/twitter-oauth-in-php_175.html 【参考方案1】:
$access_token = $twitteroauth->getAccessToken($data['oauth_verifier']);
var_dump($access_token);

$data 神奇地从何而来?您有变量 $oauth_verifier,但请记住,如果这是您注册的回调 URL,则不需要此变量。

由于您在getAccessToken 中使用了无效变量,因此它将返回无效值。

使用 TwitterOAuth 的正确方法:

if (!isset($_GET["oauth_token"])) 
    // set these values in a config file somewhere.
    $twitter = new TwitterOAuth(CONSUMER_KEY, CONSUMER_SECRET);

    // append a ?. This is your callback URL if you specify something.
    $credentials = $twitter->getRequestToken("http://example.com/test.php?");

    // try and be a bit more elegant with the URL... This is a minimal example
    $url = $twitter->getAuthorizeUrl($credentials);
    echo $url;

    // these are temporary tokens that must be used to fetch the new,
    // permanent access tokens. store these in some way,
    // session is a decent choice.
    $_SESSION["token"] = $credentials["oauth_token"];
    $_SESSION["secret"] = $credentials["oauth_token_secret"];
 else 

    // use the user's previously stored temporary credentials here
    $twitter = new TwitterOAuth(CONSUMER_KEY, CONSUMER_SECRET,
                    $_SESSION["token"], $_SESSION["secret"]);

    // uses the oauth_token (from the request) already.
    // you store these credentials in your database (see below).
    $credentials = $twitter->getAccessToken($_GET["oauth_verifier"]);

    // just a printout of credentials. store these, don't display them.
    echo "<pre>";
    var_dump($credentials);
    // valid credentials, provided you give the app access to them.
    echo "</pre>";

为了方便使用,我只使用一个脚本进行回调;如果您愿意(并且您可能应该),您可以将相关部分拆分为多个脚本。

对于您的数据库来说,凭据还包括 twitter 用户的用户名。编辑:Twitter is now allocating 64bit integers for user IDs。您应该将其存储为字符串,以确保如果您无法在应用程序的每个部分处理 64 位整数,您最终不会出现用户 ID 错误和冲突。

array(4) 
  ["oauth_token"]=>
  string(50) "7041...wYupkS"
  ["oauth_token_secret"]=>
  string(42) "O9ENq...21B2fk"
  ["user_id"]=> // user ID. always the same, never changes (store this as ID)
  string(9) "..."
  ["screen_name"]=> // username. can change.
  string(11) "..."

所以,如果你想通过 twitter 登录用户,而不明确地让他们登录到你的网站,你可以使用$_SESSION(我使用数据库登录,如果你想保存该状态,建议使用它) 在上面的脚本中,您可以将其添加到 else 块的末尾:

$_SESSION["token"] = $credentials["oauth_token"];
$_SESSION["secret"] = $credentials["oauth_secret"];
$_SESSION["username"] = $credentials["screen_name"];

如果你想给他们一个用户页面,你也可以从GET account/verify_credentials获取用户的屏幕名称和更多信息(如果你使用javascript,通过id_str在这里获取他们的用户ID):

$user_array = $twitter->get("account/verify_credentials");

【讨论】:

+1 不错的解决方案 Hiroto!但是我们如何才能得到用户的电子邮件呢? @Arash 用户电子邮件是私人的;您应该存储用户的 ID。通过电子邮件通知联系用户需要他们在明确同意的情况下向您提供电子邮件(通过将其输入表单) @Amelia 当我执行var_dump($credentials) 时,我在数组中又多了一个元素:["x_auth_expires"]=&gt; string(1) "0" 。我认为这就是它给我“无效/过期令牌”的原因。你能告诉我如何解决这个问题吗? 刚刚使用了twitter的新API,有些方法不起作用。它正在使用以下新方法: $connection = new TwitterOAuth($consumer_key, $consumer_secret); $access_token = $connection->oauth("oauth/access_token", array("oauth_verifier" => $oauth_access_token_secret)); var_dump($access_token);获取访问令牌后,在任何新页面上再次在 twitter 实例中传递新令牌。 $connection = new TwitterOAuth($consumer_key, $consumer_secret,$oauth_access_token,$oauth_access_token_secret); $content = $connection->get("account/verify_credentials");打印_r($内容);死('eee');【参考方案2】:

如果您的 OAuth 流程前一天正常工作,第二天失败,请检查您计算机的时钟。我正在运行一个 Vagrant 盒子,它不知何故将其时间设置为前一天,这导致 Twitter API 返回 "code":89,"message":"Invalid or expired token."。这也可能显示为 401 时间戳越界。您可以使用此命令在 Ubuntu 中更新您的时钟:

sudo ntpdate time.nist.gov

Alternative method 如果ntpdate 在您的系统上不可用:

sudo date -s "$(wget -qSO- --max-redirect=0 google.com 2>&1 | grep Date: | cut -d' ' -f5-8)Z"

【讨论】:

【参考方案3】:

如果不付费,则只能创建开发环境(沙盒)。

正如我已经回答here:

Counts 仅适用于付费高级帐户,并且需要付费才能使用高级访问权限。

Use this link to Apply for access.

【讨论】:

以上是关于为啥我的 twitter oauth 访问令牌无效/过期的主要内容,如果未能解决你的问题,请参考以下文章

iOS 5 Twitter 框架。获取用户的 OAuth 访问令牌

Spring Oauth2无效的访问令牌

另一个失败的 twitter oAuth cURL 访问令牌请求

使用 Firebase 登录 Facebook 导致无效 OAuth 访问令牌错误

如何从机器人聊天中获取 Twitter OAuth 访问令牌/秘密?

Twitter oauth with flask_oauthlib,无法生成请求令牌