2021-02-11 12:22:51 +00:00
|
|
|
<?php
|
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
namespace NoccyLabs\SimpleJWT\Validator;
|
2021-02-11 12:22:51 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
use NoccyLabs\SimpleJWT\JWTToken;
|
|
|
|
use NoccyLabs\SimpleJWT\Key\JWTPlaintextKey;
|
2021-02-11 12:22:51 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
class JWTValidatorTest extends \PHPUnit\Framework\TestCase
|
2021-02-11 12:22:51 +00:00
|
|
|
{
|
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
/**
|
|
|
|
* @covers
|
|
|
|
*/
|
2021-02-16 17:25:29 +00:00
|
|
|
public function testValidTokensShouldPassWithDefaultConfiguration()
|
2021-02-11 12:22:51 +00:00
|
|
|
{
|
2023-04-09 00:40:21 +00:00
|
|
|
$key = new JWTPlaintextKey("key");
|
|
|
|
$token = new JWTToken($key);
|
2021-02-11 12:22:51 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
$validator = new JWTValidator();
|
2021-02-11 12:22:51 +00:00
|
|
|
$valid = $validator->validateToken($token);
|
|
|
|
$this->assertEquals(true, $valid);
|
|
|
|
}
|
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
/**
|
|
|
|
* @covers
|
|
|
|
*/
|
2021-02-16 17:25:29 +00:00
|
|
|
public function testExpiredTokensShouldFailWithException()
|
2021-02-11 12:22:51 +00:00
|
|
|
{
|
2023-04-09 00:40:21 +00:00
|
|
|
$key = new JWTPlaintextKey("key");
|
|
|
|
$token = new JWTToken($key);
|
2021-02-11 12:22:51 +00:00
|
|
|
$token->header->set("exp", 0);
|
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
$token = new JWTToken($key, $token->getSignedToken());
|
2021-02-11 12:22:51 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
$validator = new JWTValidator();
|
|
|
|
$this->expectException(JWTTokenException::class);
|
2021-02-11 12:22:51 +00:00
|
|
|
$valid = $validator->validateToken($token);
|
|
|
|
}
|
|
|
|
|
2021-02-16 17:25:29 +00:00
|
|
|
/**
|
2023-04-09 00:40:21 +00:00
|
|
|
* @covers
|
2021-02-16 17:25:29 +00:00
|
|
|
* @dataProvider tokenGenerator
|
|
|
|
*/
|
|
|
|
public function testPinningIssuer($issuer,$audience,$key,$token)
|
|
|
|
{
|
|
|
|
$goodIssuer = "a-dom.tld";
|
2023-04-09 00:40:21 +00:00
|
|
|
$jwtKey = new JWTPlaintextKey($key);
|
|
|
|
$jwtToken = new JWTToken($jwtKey, $token);
|
2021-02-16 17:25:29 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
$validator = new JWTValidator();
|
2021-02-16 17:25:29 +00:00
|
|
|
$validator->requireIssuer($goodIssuer);
|
|
|
|
if ($goodIssuer != $issuer) {
|
2023-04-09 00:40:21 +00:00
|
|
|
$this->expectException(JWTTokenException::class);
|
2021-02-16 17:25:29 +00:00
|
|
|
}
|
|
|
|
$valid = $validator->validateToken($jwtToken);
|
|
|
|
if ($goodIssuer == $issuer) {
|
|
|
|
$this->assertTrue($valid);
|
|
|
|
}
|
|
|
|
}
|
2021-02-17 21:22:15 +00:00
|
|
|
|
|
|
|
/**
|
2023-04-09 00:40:21 +00:00
|
|
|
* @covers
|
2021-02-17 21:22:15 +00:00
|
|
|
* @dataProvider tokenGenerator
|
|
|
|
*/
|
|
|
|
public function testPinningAudience($issuer,$audience,$key,$token)
|
|
|
|
{
|
|
|
|
$goodAudience = [ "a-dom.tld", "app.a-dom.tld" ];
|
2023-04-09 00:40:21 +00:00
|
|
|
$jwtKey = new JWTPlaintextKey($key);
|
|
|
|
$jwtToken = new JWTToken($jwtKey, $token);
|
2021-02-17 21:22:15 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
$validator = new JWTValidator();
|
2021-02-17 21:22:15 +00:00
|
|
|
$validator->requireAudience($goodAudience);
|
|
|
|
if (!in_array($audience, $goodAudience)) {
|
2023-04-09 00:40:21 +00:00
|
|
|
$this->expectException(JWTTokenException::class);
|
2021-02-17 21:22:15 +00:00
|
|
|
}
|
|
|
|
$valid = $validator->validateToken($jwtToken);
|
|
|
|
if (in_array($audience, $goodAudience)) {
|
|
|
|
$this->assertTrue($valid);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
2023-04-09 00:40:21 +00:00
|
|
|
* @covers
|
2021-02-17 21:22:15 +00:00
|
|
|
* @dataProvider tokenGenerator
|
|
|
|
*/
|
|
|
|
public function testPinningBoth($issuer,$audience,$key,$token)
|
|
|
|
{
|
|
|
|
$goodIssuer = "a-dom.tld";
|
|
|
|
$goodAudience = [ "a-dom.tld", "app.a-dom.tld" ];
|
2023-04-09 00:40:21 +00:00
|
|
|
$jwtKey = new JWTPlaintextKey($key);
|
|
|
|
$jwtToken = new JWTToken($jwtKey, $token);
|
2021-02-17 21:22:15 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
$validator = new JWTValidator();
|
2021-02-17 21:22:15 +00:00
|
|
|
$validator->requireIssuer($goodIssuer);
|
|
|
|
$validator->requireAudience($goodAudience);
|
|
|
|
if (($goodIssuer != $issuer) || (!in_array($audience, $goodAudience))) {
|
2023-04-09 00:40:21 +00:00
|
|
|
$this->expectException(JWTTokenException::class);
|
2021-02-17 21:22:15 +00:00
|
|
|
}
|
|
|
|
$valid = $validator->validateToken($jwtToken);
|
|
|
|
if (($goodIssuer == $issuer) && (in_array($audience, $goodAudience))) {
|
|
|
|
$this->assertTrue($valid);
|
|
|
|
}
|
|
|
|
}
|
2021-02-16 17:25:29 +00:00
|
|
|
|
2023-04-09 00:40:21 +00:00
|
|
|
public static function tokenGenerator()
|
2021-02-16 17:25:29 +00:00
|
|
|
{
|
|
|
|
$keyrand = function () {
|
|
|
|
return substr(sha1(microtime(true).rand(0,65535)), 5, 10);
|
|
|
|
};
|
|
|
|
$token = function ($head,$claims,$key) {
|
2023-04-09 00:40:21 +00:00
|
|
|
$jwtKey = new JWTPlaintextKey($key);
|
|
|
|
$tok = new JWTToken($jwtKey);
|
2021-02-16 17:25:29 +00:00
|
|
|
$tok->header->setAll($head);
|
|
|
|
$tok->claims->setAll($claims);
|
|
|
|
return $tok->getSignedToken();
|
|
|
|
};
|
|
|
|
$row = function ($iss, $aud, array $claims) use ($keyrand, $token) {
|
|
|
|
$key = $keyrand();
|
2023-04-09 00:40:21 +00:00
|
|
|
$jwtKey = new JWTPlaintextKey($key);
|
2021-02-16 17:25:29 +00:00
|
|
|
return [
|
|
|
|
$iss,
|
|
|
|
$aud,
|
|
|
|
$key,
|
|
|
|
$token(['iss'=>$iss, 'aud'=>$aud], $claims, $key),
|
|
|
|
];
|
|
|
|
};
|
|
|
|
|
|
|
|
return [
|
|
|
|
$row("a-dom.tld", "a-dom.tld", []),
|
|
|
|
$row("b-dom.tld", "a-dom.tld", []),
|
|
|
|
$row("b-dom.tld", "b-dom.tld", []),
|
2021-02-17 21:22:15 +00:00
|
|
|
$row("a-dom.tld", "app.a-dom.tld", []),
|
|
|
|
$row("a-dom.tld", "app.b-dom.tld", []),
|
|
|
|
$row("", "app.b-dom.tld", []),
|
2021-02-16 17:25:29 +00:00
|
|
|
];
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|