<?php declare(strict_types=1); namespace ShlinkioTest\Shlink\Rest\Authentication; use Firebase\JWT\JWT; use PHPUnit\Framework\TestCase; use Shlinkio\Shlink\Core\Options\AppOptions; use Shlinkio\Shlink\Rest\Authentication\JWTService; use Shlinkio\Shlink\Rest\Entity\ApiKey; class JWTServiceTest extends TestCase { /** * @var JWTService */ protected $service; public function setUp() { $this->service = new JWTService(new AppOptions([ 'name' => 'ShlinkTest', 'version' => '10000.3.1', 'secret_key' => 'foo', ])); } /** * @test */ public function tokenIsProperlyCreated() { $id = '34'; $token = $this->service->create((new ApiKey())->setId($id)); $payload = (array) JWT::decode($token, 'foo', [JWTService::DEFAULT_ENCRYPTION_ALG]); $this->assertGreaterThanOrEqual($payload['iat'], time()); $this->assertGreaterThan(time(), $payload['exp']); $this->assertEquals($id, $payload['key']); $this->assertEquals('auth', $payload['sub']); $this->assertEquals('ShlinkTest:v10000.3.1', $payload['iss']); } /** * @test */ public function refreshIncreasesExpiration() { $originalLifetime = 10; $newLifetime = 30; $originalPayload = ['exp' => time() + $originalLifetime]; $token = JWT::encode($originalPayload, 'foo'); $newToken = $this->service->refresh($token, $newLifetime); $newPayload = (array) JWT::decode($newToken, 'foo', [JWTService::DEFAULT_ENCRYPTION_ALG]); $this->assertGreaterThan($originalPayload['exp'], $newPayload['exp']); } /** * @test */ public function verifyReturnsTrueWhenTheTokenIsCorrect() { $this->assertTrue($this->service->verify(JWT::encode([], 'foo'))); } /** * @test */ public function verifyReturnsFalseWhenTheTokenIsCorrect() { $this->assertFalse($this->service->verify('invalidToken')); } /** * @test */ public function getPayloadWorksWithCorrectTokens() { $originalPayload = [ 'exp' => time() + 10, 'sub' => 'testing', ]; $token = JWT::encode($originalPayload, 'foo'); $this->assertEquals($originalPayload, $this->service->getPayload($token)); } /** * @test * @expectedException \Shlinkio\Shlink\Rest\Exception\AuthenticationException */ public function getPayloadThrowsExceptionWithIncorrectTokens() { $this->service->getPayload('invalidToken'); } }