From 8bfc9fcc6ed2ea920394c118293c157cbe0a91ba Mon Sep 17 00:00:00 2001 From: Timothy J Warren Date: Mon, 19 Jun 2017 15:31:24 -0400 Subject: [PATCH] Attempt to re-authenticate when access token expires --- src/API/Kitsu.php | 2 ++ src/API/Kitsu/Auth.php | 74 ++++++++++++++++++++++++++++++++++++++++- src/API/Kitsu/Model.php | 28 +++++++++++++++- 3 files changed, 102 insertions(+), 2 deletions(-) diff --git a/src/API/Kitsu.php b/src/API/Kitsu.php index c2e3ca03..bbebf196 100644 --- a/src/API/Kitsu.php +++ b/src/API/Kitsu.php @@ -26,6 +26,8 @@ class Kitsu { const AUTH_URL = 'https://kitsu.io/api/oauth/token'; const AUTH_USER_ID_KEY = 'kitsu-auth-userid'; const AUTH_TOKEN_CACHE_KEY = 'kitsu-auth-token'; + const AUTH_TOKEN_EXP_CACHE_KEY = 'kitsu-auth-token-expires'; + const AUTH_TOKEN_REFRESH_CACHE_KEY = 'kitsu-auth-token-refresh'; /** * Determine whether an anime is airing, finished airing, or has not yet aired diff --git a/src/API/Kitsu/Auth.php b/src/API/Kitsu/Auth.php index 84f41f18..743c1d95 100644 --- a/src/API/Kitsu/Auth.php +++ b/src/API/Kitsu/Auth.php @@ -90,13 +90,74 @@ class Auth { $cacheItem->set($auth['access_token']); $cacheItem->save(); + // Set the token expiration in the cache + $expire_time = $auth['created_at'] + $auth['expires_in']; + $cacheItem = $this->cache->getItem(K::AUTH_TOKEN_EXP_CACHE_KEY); + $cacheItem->set($expire_time); + $cacheItem->save(); + + // Set the refresh token in the cache + $cacheItem = $this->cache->getItem(K::AUTH_TOKEN_REFRESH_CACHE_KEY); + $cacheItem->set($auth['refresh_token']); + $cacheItem->save(); + + // Set the session values $this->segment->set('auth_token', $auth['access_token']); + $this->segment->set('auth_token_expires', $expire_time); + $this->segment->set('refresh_token', $auth['refresh_token']); return TRUE; } return FALSE; } + + /** + * Make the call to re-authenticate with the existing refresh token + * + * @param string $token + * @return boolean + */ + public function reAuthenticate(string $token) + { + try + { + $auth = $this->model->reAuthenticate($token); + } + catch (Exception $e) + { + return FALSE; + } + + if (FALSE !== $auth) + { + // Set the token in the cache for command line operations + $cacheItem = $this->cache->getItem(K::AUTH_TOKEN_CACHE_KEY); + $cacheItem->set($auth['access_token']); + $cacheItem->save(); + + // Set the token expiration in the cache + $expire_time = $auth['created_at'] + $auth['expires_in']; + $cacheItem = $this->cache->getItem(K::AUTH_TOKEN_EXP_CACHE_KEY); + $cacheItem->set($expire_time); + $cacheItem->save(); + + // Set the refresh token in the cache + $cacheItem = $this->cache->getItem(K::AUTH_TOKEN_REFRESH_CACHE_KEY); + $cacheItem->set($auth['refresh_token']); + $cacheItem->save(); + + // Set the session values + $this->segment->set('auth_token', $auth['access_token']); + $this->segment->set('auth_token_expires', $expire_time); + $this->segment->set('refresh_token', $auth['refresh_token']); + return TRUE; + } + + return FALSE; + } + + /** * Check whether the current user is authenticated * @@ -124,7 +185,18 @@ class Auth { */ public function get_auth_token() { - return $this->segment->get('auth_token', FALSE); + $token = $this->segment->get('auth_token', FALSE); + $refresh_token = $this->segment->get('refresh_token', FALSE); + $isExpired = time() > $this->segment->get('auth_token_expires', 0); + + // Attempt to re-authenticate with refresh token + if ($isExpired && $refresh_token) + { + $reauthenticated = $this->reAuthenticate($refresh_token); + return $this->segment->get('auth_token', FALSE); + } + + return $token; } } // End of KitsuAuth.php \ No newline at end of file diff --git a/src/API/Kitsu/Model.php b/src/API/Kitsu/Model.php index 88b109fd..02ed1066 100644 --- a/src/API/Kitsu/Model.php +++ b/src/API/Kitsu/Model.php @@ -97,7 +97,7 @@ class Model { * * @param string $username * @param string $password - * @return bool|string + * @return bool|array */ public function authenticate(string $username, string $password) { @@ -120,6 +120,32 @@ class Model { return FALSE; } + /** + * Extend the current session with a refresh token + * + * @param string $token + * @return bool|array + */ + public function reAuthenticate(string $token) + { + $response = $this->getResponse('POST', K::AUTH_URL, [ + 'headers' => [], + 'form_params' => [ + 'grant_type' => 'refresh_token', + 'refresh_token' => $token + ] + ]); + + $data = Json::decode((string)$response->getBody()); + + if (array_key_exists('access_token', $data)) + { + return $data; + } + + return FALSE; + } + /** * Get the userid for a username from Kitsu *