diff --git a/app/Auth/Access/Oidc/OidcJwtSigningKey.php b/app/Auth/Access/Oidc/OidcJwtSigningKey.php index a70f3b3c7..012a6cbf9 100644 --- a/app/Auth/Access/Oidc/OidcJwtSigningKey.php +++ b/app/Auth/Access/Oidc/OidcJwtSigningKey.php @@ -60,8 +60,11 @@ class OidcJwtSigningKey */ protected function loadFromJwkArray(array $jwk) { - if ($jwk['alg'] !== 'RS256') { - throw new OidcInvalidKeyException("Only RS256 keys are currently supported. Found key using {$jwk['alg']}"); + // 'alg' is optional for a JWK, but we will still attempt to validate if + // it exists otherwise presume it will be compatible. + $alg = $jwk['alg'] ?? null; + if ($jwk['kty'] !== 'RSA' || !(is_null($alg) || $alg === 'RS256')) { + throw new OidcInvalidKeyException("Only RS256 keys are currently supported. Found key using {$alg}"); } if (empty($jwk['use'])) { diff --git a/app/Auth/Access/Oidc/OidcProviderSettings.php b/app/Auth/Access/Oidc/OidcProviderSettings.php index 32946d058..016d006d2 100644 --- a/app/Auth/Access/Oidc/OidcProviderSettings.php +++ b/app/Auth/Access/Oidc/OidcProviderSettings.php @@ -164,7 +164,8 @@ class OidcProviderSettings protected function filterKeys(array $keys): array { return array_filter($keys, function (array $key) { - return $key['kty'] === 'RSA' && $key['use'] === 'sig' && $key['alg'] === 'RS256'; + $alg = $key['alg'] ?? null; + return $key['kty'] === 'RSA' && $key['use'] === 'sig' && (is_null($alg) || $alg === 'RS256'); }); } diff --git a/tests/Auth/OidcTest.php b/tests/Auth/OidcTest.php index 0b033ea81..9fa4d0012 100644 --- a/tests/Auth/OidcTest.php +++ b/tests/Auth/OidcTest.php @@ -318,6 +318,31 @@ class OidcTest extends TestCase $this->assertCount(4, $transactions); } + public function test_auth_login_with_autodiscovery_with_keys_that_do_not_have_alg_property() + { + $this->withAutodiscovery(); + + $keyArray = OidcJwtHelper::publicJwkKeyArray(); + unset($keyArray['alg']); + + $this->mockHttpClient([ + $this->getAutoDiscoveryResponse(), + new Response(200, [ + 'Content-Type' => 'application/json', + 'Cache-Control' => 'no-cache, no-store', + 'Pragma' => 'no-cache', + ], json_encode([ + 'keys' => [ + $keyArray, + ], + ])), + ]); + + $this->assertFalse(auth()->check()); + $this->runLogin(); + $this->assertTrue(auth()->check()); + } + protected function withAutodiscovery() { config()->set([