Select Git revision
TokenChecker.php
-
Sonia Zorba authoredSonia Zorba authored
TokenChecker.php 2.22 KiB
<?php
namespace RAP;
use \Firebase\JWT\JWT;
class TokenChecker {
private $locator;
public function __construct(Locator $locator) {
$this->locator = $locator;
}
public function validateToken(): object {
$headers = apache_request_headers();
if (!isset($headers['Authorization'])) {
throw new BadRequestException("Missing Authorization header");
}
$authorizationHeader = explode(" ", $headers['Authorization']);
if ($authorizationHeader[0] === "Bearer") {
$token = $authorizationHeader[1];
} else {
throw new BadRequestException("Invalid token type");
}
return $this->getValidTokenObject($token);
}
public function getValidTokenObject(string $jwt): object {
$jwtParts = explode('.', $jwt);
if (count($jwtParts) === 0) {
throw new UnauthorizedException("Invalid token");
}
$header = JWT::jsonDecode(JWT::urlsafeB64Decode($jwtParts[0]));
if (!isset($header->kid)) {
throw new UnauthorizedException("Invalid token: missing kid in header");
}
$keyPair = $this->locator->getJWKSDAO()->getRSAKeyPairById($header->kid);
if ($keyPair === null) {
throw new UnauthorizedException("Invalid kid: no key found");
}
try {
$token = JWT::decode($jwt, $keyPair->publicKey, [$keyPair->alg]);
if (!isset($token->sub)) {
throw new UnauthorizedException("Invalid token: missing subject claim");
}
return $token;
} catch (\Firebase\JWT\ExpiredException $ex) {
throw new UnauthorizedException("Access token is expired");
}
}
public function checkScope(object $tokenData, string $desiredScope): void {
if (!(isset($tokenData->scope))) {
throw new UnauthorizedException("Missing 'scope' claim in access token");
}
$scopes = explode(' ', $tokenData->scope);
foreach ($scopes as $scope) {
if ($scope === $desiredScope) {
return;
}
}
throw new UnauthorizedException("Scope '$desiredScope' is required for performing this action");
}
}