From 4e816ffcd689bf80cf2edc7706157a2d24f62103 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 3 Oct 2025 17:01:20 +0000 Subject: [PATCH 1/4] Initial plan From 690a28e65290c402ce0f327f2cb52e0fba34b084 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 3 Oct 2025 17:20:45 +0000 Subject: [PATCH 2/4] Implement Token Based Auth Controller Co-authored-by: MichaelJ2324 <3056352+MichaelJ2324@users.noreply.github.com> --- .../Abstracts/AbstractTokenController.php | 81 ++++++++++++ src/Auth/TokenAuthController.php | 7 ++ tests/Auth/AbstractTokenControllerTest.php | 119 ++++++++++++++++++ 3 files changed, 207 insertions(+) create mode 100644 src/Auth/Abstracts/AbstractTokenController.php create mode 100644 src/Auth/TokenAuthController.php create mode 100644 tests/Auth/AbstractTokenControllerTest.php diff --git a/src/Auth/Abstracts/AbstractTokenController.php b/src/Auth/Abstracts/AbstractTokenController.php new file mode 100644 index 0000000..aab3308 --- /dev/null +++ b/src/Auth/Abstracts/AbstractTokenController.php @@ -0,0 +1,81 @@ +setToken($credentials['token']); + } + + return $this; + } + + /** + * Token-based auth is authenticated if a token is present + * @inheritdoc + */ + public function isAuthenticated(): bool + { + return !empty($this->token); + } + + /** + * For token-based auth, authentication is always successful if token is set + * No API call needed + * @inheritdoc + */ + public function authenticate(): bool + { + return $this->isAuthenticated(); + } + + /** + * For token-based auth, logout just clears the token + * No API call needed + * @inheritdoc + */ + public function logout(): bool + { + $this->clearToken(); + $this->removeCachedToken(); + return true; + } + + /** + * Get the Value to be set on the Auth Header + * For token auth, just use the token directly + */ + protected function getAuthHeaderValue(): string + { + return $this->authType . " " . $this->getToken(); + } +} diff --git a/src/Auth/TokenAuthController.php b/src/Auth/TokenAuthController.php new file mode 100644 index 0000000..5f9c6a0 --- /dev/null +++ b/src/Auth/TokenAuthController.php @@ -0,0 +1,7 @@ +assertEquals(false, $Auth->isAuthenticated()); + + $Auth->setCredentials(['token' => 'my-api-token-12345']); + $this->assertEquals(true, $Auth->isAuthenticated()); + $this->assertEquals('my-api-token-12345', $Auth->getToken()); + } + + /** + * @covers ::authenticate + */ + public function testAuthenticate(): void + { + $Auth = new TokenAuthController(); + + // Authentication should fail without token + $this->assertEquals(false, $Auth->authenticate()); + + // Authentication should succeed with token + $Auth->setCredentials(['token' => 'my-api-token-12345']); + $this->assertEquals(true, $Auth->authenticate()); + } + + /** + * @covers ::logout + * @covers ::isAuthenticated + */ + public function testLogout(): void + { + $Auth = new TokenAuthController(); + $Auth->setCredentials(['token' => 'my-api-token-12345']); + + $this->assertEquals(true, $Auth->isAuthenticated()); + $this->assertEquals(true, $Auth->logout()); + $this->assertEquals(false, $Auth->isAuthenticated()); + } + + /** + * @covers ::__construct + */ + public function testNoAuthActions(): void + { + $Auth = new TokenAuthController(); + + // Token auth should not have authenticate/logout actions + $actions = $Auth->getActions(); + $this->assertEmpty($actions); + } + + /** + * Test setting token directly + */ + public function testSetToken(): void + { + $Auth = new TokenAuthController(); + $Auth->setToken('direct-token-67890'); + + $this->assertEquals(true, $Auth->isAuthenticated()); + $this->assertEquals('direct-token-67890', $Auth->getToken()); + } + + /** + * @covers ::getAuthHeaderValue + */ + public function testAuthHeaderValue(): void + { + $Auth = new TokenAuthController(); + $Auth->setCredentials(['token' => 'my-api-token-12345']); + + // Use reflection to test protected method + $class = new \ReflectionClass($Auth); + $method = $class->getMethod('getAuthHeaderValue'); + $method->setAccessible(true); + + $headerValue = $method->invoke($Auth); + $this->assertEquals('Bearer my-api-token-12345', $headerValue); + } +} From a3836d7202a75cc05b46922f2bc5222d3c314194 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Fri, 3 Oct 2025 17:22:57 +0000 Subject: [PATCH 3/4] Add documentation and remove unused import from AbstractTokenController Co-authored-by: MichaelJ2324 <3056352+MichaelJ2324@users.noreply.github.com> --- src/Auth/Abstracts/AbstractTokenController.php | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/src/Auth/Abstracts/AbstractTokenController.php b/src/Auth/Abstracts/AbstractTokenController.php index aab3308..5625d97 100644 --- a/src/Auth/Abstracts/AbstractTokenController.php +++ b/src/Auth/Abstracts/AbstractTokenController.php @@ -2,8 +2,6 @@ namespace MRussell\REST\Auth\Abstracts; -use GuzzleHttp\Psr7\Request; - /** * Class AbstractTokenController * @@ -11,6 +9,20 @@ * pre-configured API tokens passed via Bearer Authorization header. * No authenticate/logout flow required. * + * Usage Example: + * ```php + * $auth = new TokenAuthController(); + * $auth->setCredentials(['token' => 'your-api-token-here']); + * + * // The token will be automatically added to requests as: + * // Authorization: Bearer your-api-token-here + * + * // Check if authenticated + * if ($auth->isAuthenticated()) { + * // Token is set and ready to use + * } + * ``` + * * @package MRussell\REST\Auth\Abstracts */ abstract class AbstractTokenController extends AbstractBasicController From b1508655149914e46ae09a9915ffe24cd74bfda7 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Mon, 6 Oct 2025 00:08:12 +0000 Subject: [PATCH 4/4] Support both 'token' and 'api_token' properties for backward compatibility Co-authored-by: MichaelJ2324 <3056352+MichaelJ2324@users.noreply.github.com> --- .../Abstracts/AbstractTokenController.php | 8 +++++ tests/Auth/AbstractTokenControllerTest.php | 32 +++++++++++++++++++ 2 files changed, 40 insertions(+) diff --git a/src/Auth/Abstracts/AbstractTokenController.php b/src/Auth/Abstracts/AbstractTokenController.php index 5625d97..29a389b 100644 --- a/src/Auth/Abstracts/AbstractTokenController.php +++ b/src/Auth/Abstracts/AbstractTokenController.php @@ -12,8 +12,13 @@ * Usage Example: * ```php * $auth = new TokenAuthController(); + * + * // Use 'token' property (recommended) * $auth->setCredentials(['token' => 'your-api-token-here']); * + * // Or use 'api_token' property (backward compatibility) + * $auth->setCredentials(['api_token' => 'your-api-token-here']); + * * // The token will be automatically added to requests as: * // Authorization: Bearer your-api-token-here * @@ -44,8 +49,11 @@ public function setCredentials(array $credentials): static parent::setCredentials($credentials); // If a token is provided in credentials, set it directly + // Support both 'token' and 'api_token' for backward compatibility if (isset($credentials['token'])) { $this->setToken($credentials['token']); + } elseif (isset($credentials['api_token'])) { + $this->setToken($credentials['api_token']); } return $this; diff --git a/tests/Auth/AbstractTokenControllerTest.php b/tests/Auth/AbstractTokenControllerTest.php index c22982d..a672cf9 100644 --- a/tests/Auth/AbstractTokenControllerTest.php +++ b/tests/Auth/AbstractTokenControllerTest.php @@ -47,6 +47,38 @@ public function testSetCredentials(): void $this->assertEquals('my-api-token-12345', $Auth->getToken()); } + /** + * @covers ::setCredentials + * @covers ::isAuthenticated + */ + public function testSetCredentialsWithApiToken(): void + { + $Auth = new TokenAuthController(); + $this->assertEquals(false, $Auth->isAuthenticated()); + + // Test backward compatibility with 'api_token' property + $Auth->setCredentials(['api_token' => 'my-api-token-67890']); + $this->assertEquals(true, $Auth->isAuthenticated()); + $this->assertEquals('my-api-token-67890', $Auth->getToken()); + } + + /** + * @covers ::setCredentials + * @covers ::isAuthenticated + */ + public function testSetCredentialsTokenTakesPrecedence(): void + { + $Auth = new TokenAuthController(); + + // If both 'token' and 'api_token' are provided, 'token' should take precedence + $Auth->setCredentials([ + 'token' => 'token-value', + 'api_token' => 'api-token-value' + ]); + $this->assertEquals(true, $Auth->isAuthenticated()); + $this->assertEquals('token-value', $Auth->getToken()); + } + /** * @covers ::authenticate */