【问题标题】:Refresh Tokens Google OAuth 2.0 PHP刷新令牌 Google OAuth 2.0 PHP
【发布时间】:2015-02-02 02:06:41
【问题描述】:

使用来自本网站https://github.com/google/google-api-php-client的 Google OAuth 2.0 代码

我需要帮助将刷新令牌编码到以下代码中,我不知道该怎么做,那里有很多资源,但我找不到任何可以帮助我将其合并到我的代码中的资源。现在的问题是,如果我让令牌过期,它会给我一个错误,说我没有刷新令牌,我需要它,因为我不想对 accesstype 使用 force 选项。我正在使用php客户端:

    //include google api files
    require_once 'src/Google/Client.php';
    require_once 'src/Google/Service/Oauth2.php';

    //start session
    $client_id = 'xxxx';
    $client_secret = 'xxxx';
    $redirect_uri = 'xxxxx';

    $client = new Google_Client();
    $client->setApplicationName("Backpack Em");
    $client->setClientId($client_id);
    $client->setClientSecret($client_secret);
    $client->setRedirectUri($redirect_uri);
    $client->setScopes(array('https://www.googleapis.com/auth/userinfo.email','https://www.googleapis.com/auth/userinfo.profile'));
    $client->setAccessType('offline');
    $service = new Google_Service_Oauth2 ($client);

 if (isset($_REQUEST['logout'])) {
  unset($_SESSION['upload_token']);
  $client->revokeToken();   //added
  header('Location: ' . filter_var($redirect_uri, FILTER_SANITIZE_URL));     //redirect user back to page
}

if (isset($_GET['code'])) {
  $client->authenticate($_GET['code']);
  $_SESSION['upload_token'] = $client->getAccessToken();
  $redirect = 'http://' . $_SERVER['HTTP_HOST'] . $_SERVER['PHP_SELF'];       header('Location: ' . filter_var($redirect, FILTER_SANITIZE_URL));
}

if (isset($_SESSION['upload_token']) && $_SESSION['upload_token']) {
  $client->setAccessToken($_SESSION['upload_token']);
  if ($client->isAccessTokenExpired()) {
    unset($_SESSION['upload_token']);
  }
}

if ($client->getAccessToken()) 
  {
    //For logged in user, get details from google using access token
    $user           = $service->userinfo->get($params);
    //$user_id          = filter_var($user['id'],FILTER_SANITIZE_SPECIAL_CHARS);
    $user_name          = filter_var($user['name'], FILTER_SANITIZE_SPECIAL_CHARS);
    $first_name         = filter_var($user['given_name'], FILTER_SANITIZE_SPECIAL_CHARS);
    $last_name          = filter_var($user['family_name'], FILTER_SANITIZE_SPECIAL_CHARS);
    $email          = filter_var($user['email'], FILTER_SANITIZE_EMAIL);
    $profile_url        = filter_var($user['link'], FILTER_VALIDATE_URL);
    $profile_image_url      = filter_var($user['picture'], FILTER_VALIDATE_URL);
    $gender         = filter_var($user['gender'], FILTER_SANITIZE_SPECIAL_CHARS);
    $personMarkup       = "$email<div><img src='$profile_image_url?sz=50'></div>";
    $_SESSION['upload_token']   = $client->getAccessToken();
    $_SESSION['upload_token']   = $client->getRefreshToken();

  }

else
  {
  $authUrl = $client->createAuthUrl();
  }
?>

【问题讨论】:

    标签: php oauth-2.0 google-oauth


    【解决方案1】:

    将刷新令牌存储在会话中:

    $refresh_token = $client->getRefreshToken();
    $_SESSION['refresh_token'] = $refresh_token;
    

    当你想获得一个新的访问令牌时,你可以调用:

    $refresh_token = $_SESSION['refresh_token'];
    $client->refreshToken($refreshToken);
    $access_token = $client->getAccessToken();
    $_SESSION['upload_token'] = $access_token;
    

    您可以致电$client&gt;isAccessTokenExpired() 以查看访问令牌是否已过期并且您需要触发刷新流程。

    要打印/访问expires_in 值,您可以使用:

    $json = json_decode($client->getAccessToken());
    echo $json['expires_in'];
    

    但请注意,expires_in 与创建令牌的时间相关,因此要检查令牌是否已过期,您可以使用:

    $expired = ($json['created'] + $json['expires_in']) < time();
    

    【讨论】:

    • 命令中的 expires 在哪里?我把它放在我的代码中的哪个位置也有关系吗?
    • isAccessTokenExpired上添加了注释
    • 我相信有一个命令 expires_in: () 来告诉刷新令牌何时过期。你知道这是去哪里吗?
    • 为此添加了一个示例
    • 谢谢,你以前用过这个吗?我无法将它与我的代码集成。我在哪里把它放在我的代码中?另外,您知道使用这些刷新令牌的工作演示吗?
    【解决方案2】:

    老问题,但我希望这仍然可以帮助某人。 这些是我为服务器端令牌刷新所遵循的步骤(无需用户登录)。

    1. 在 Google Developer Console 应用程序中,为 OAuth 创建一个新的客户端 ID,使用“https://developers.google.com/oauthplayground”作为重定向 uri。 (你需要这个在操场上进行身份验证)
    2. https://developers.google.com/oauthplayground/ 中,单击右上角的设置图标并选中“使用您自己的OAuth 凭据”。您必须插入在第 1 点生成的有效凭据(客户端 ID 和客户端密码)。
    3. 在左栏中选择并授权您的 API(“步骤 1”)
    4. 获得授权码后,将其兑换成令牌(“步骤 2”)
    5. 现在,您可以在脚本中使用客户端 ID、客户端密码(您在第 2 点使用的相同)和刷新令牌(您在第 4 点获得的那个)。

    这是我正在使用的工作代码(例如用于分析):

    $clientId = 'xxxxxxxxxxxxxxxxx'; // from google developer console
    $clientSecret = 'xxxxxxxxxxxxxx'; // from google developer console
    $refreshToken = 'xxxxxxxxxx'; // from https://developers.google.com/oauthplayground/
    $client = new Google_Client();
    $client->setClientId($clientId);
    $client->setClientSecret($clientSecret);
    $client->refreshToken($refreshToken);
    $access_token = $client->getAccessToken();
    $client->setAccessToken($access_token);
    $analytics = new Google_Service_Analytics($client);
    $response = $analytics->data_ga->get(
       'ga:' . xxxxxxx, 
       '7daysAgo',
       'today',
       'ga:sessions');
    

    【讨论】:

    • 这个刷新令牌是从哪里来的?我认为刷新令牌是在用户登录时生成的,所以它将是一个唯一的令牌。如果我错了,请纠正我。
    • 你是对的,在我的例子中你不需要用户登录。我刚刚更新了我的答案。
    • 那么如果我从playgroud获得刷新令牌,它会在一个小时后自动刷新登录用户?刷新令牌持续多久?
    • 在我的应用程序中,当我需要调用 api 时,我对访问令牌(通过刷新令牌)发出了新请求。据我所知,刷新令牌不会过期。
    • 你能解释一下我是如何从操场上得到这个刷新令牌的吗?它可以只是一个随机的刷新令牌,还是需要特定于我的客户端 ID?