'Google Oauth2 for website (php) - can't get my head around access tokens

I am trying to implement a simple Google login for a website I am building. I am using PHP as scripting language and have created a login script that looks as follows:

<?php
    require_once  $_SERVER['DOCUMENT_ROOT'] . '/login/vendor/autoload.php';
    require_once  $_SERVER['DOCUMENT_ROOT'] . '/lib/db.class.php';
    
    $client = new \Google_Client();
    $client->setAuthConfig($_SERVER['DOCUMENT_ROOT'] . '/login/credentials.json');
    $client->setAccessType('offline');
    $client->setPrompt("consent");
    $client->addScope('email');
    $client->addScope('profile');
    
    $dbx = new db();
    $rt = $dbx->get_token();
    
    if ($rt) {
         $accessToken = $rt;
         $client->setAccessToken($accessToken);
    }
    
    if ($client->isAccessTokenExpired()) {
        $grt = $client->getRefreshToken(); 
        if ($grt) {
            $client->fetchAccessTokenWithRefreshToken($grt);
            $client->setAccessToken($accessToken);
            $dbx->set_token($client->getAccessToken());
        } else if($_GET['code']) {
                $accessToken = $client->fetchAccessTokenWithAuthCode($_GET['code']);
                $client->setAccessToken($accessToken);
                $dbx->set_token($client->getAccessToken());
        } else {
            header('location:' . $client->createAuthUrl());
        }
    }
      
    $service = new Google_Service_Oauth2($client);
    $userdata = $service->userinfo->get();
?>

To logout, I have the following script

<?php

require_once $_SERVER['DOCUMENT_ROOT'].'/login/vendor/autoload.php';
require_once  $_SERVER['DOCUMENT_ROOT'] . '/lib/db.class.php';

$dbx = new db();
$accessToken = $dbx->get_token();

$client = new \Google_Client();

//Reset OAuth access token
$client->revokeToken($accessToken);

?>

Now if I call the login script after running the logout script, the following error is thrown

Fatal error: Uncaught Google\Service\Exception: { "error": { "code": 401, "message": "Request is missing required authentication credential. Expected OAuth 2 access token, login cookie or other valid authentication credential. See https://developers.google.com/identity/sign-in/web/devconsole-project.", "errors": [ { "message": "Request is missing required authentication credential. Expected OAuth 2 access token, login cookie or other valid authentication credential. See https://developers.google.com/identity/sign-in/web/devconsole-project.", "domain": "global", "reason": "unauthorized" } ], "status": "UNAUTHENTICATED" } } in /var/www/vhosts/kiwidb.nz/httpdocs/login/vendor/google/apiclient/src/Http/REST.php:128 Stack trace: #0 /var/www/vhosts/kiwidb.nz/httpdocs/login/vendor/google/apiclient/src/Http/REST.php(103): Google\Http\REST::decodeHttpResponse(Object(GuzzleHttp\Psr7\Response), Object(GuzzleHttp\Psr7\Request), 'Google_Service_...') 

I assume the problem is that the access token has been revoked by calling the logout script, but the login script still finds the already revoked access token in the database.

The core issue is that I fully haven't gotten my head around the concept of the access token. Are individual access tokens generated for every user? Or, as I thought, is there one app (int his case the website) specific access token? In which case I don't get the Fatal error...



Solution 1:[1]

OAuth Access Tokens are generated per user. They are valid for 3,600 seconds.

You are making a common mistake. You are storing the Access Token in the database. Only store the OAuth Refresh Token. Store the user's access token encrypted in the session cookie. If the access token has expired, then you use the refresh token to request a new access token for the user.

Also, do not log out the user by calling a Google endpoint as that logs the user out of all their other sites as well. Instead, delete the refresh token from your database, clean up the session, etc.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 John Hanley