diff --git a/server/api/controllers/access-tokens/exchange-using-oidc.js b/server/api/controllers/access-tokens/exchange-using-oidc.js index 1fcf06e0..c1aa7d27 100644 --- a/server/api/controllers/access-tokens/exchange-using-oidc.js +++ b/server/api/controllers/access-tokens/exchange-using-oidc.js @@ -6,6 +6,9 @@ const Errors = { INVALID_CODE_OR_NONCE: { invalidCodeOrNonce: 'Invalid code or nonce', }, + INVALID_OIDC_CONFIGURATION: { + invalidOIDCConfiguration: 'Invalid OIDC configuration', + }, INVALID_USERINFO_CONFIGURATION: { invalidUserinfoConfiguration: 'Invalid userinfo configuration', }, @@ -37,6 +40,9 @@ module.exports = { }, exits: { + invalidOIDCConfiguration: { + responseType: 'serverError', + }, invalidCodeOrNonce: { responseType: 'unauthorized', }, @@ -63,6 +69,7 @@ module.exports = { sails.log.warn(`Invalid code or nonce! (IP: ${remoteAddress})`); return Errors.INVALID_CODE_OR_NONCE; }) + .intercept('invalidOIDCConfiguration', () => Errors.INVALID_OIDC_CONFIGURATION) .intercept('invalidUserinfoConfiguration', () => Errors.INVALID_USERINFO_CONFIGURATION) .intercept('emailAlreadyInUse', () => Errors.EMAIL_ALREADY_IN_USE) .intercept('usernameAlreadyInUse', () => Errors.USERNAME_ALREADY_IN_USE) diff --git a/server/api/controllers/show-config.js b/server/api/controllers/show-config.js index 1a8207ec..d0acd861 100644 --- a/server/api/controllers/show-config.js +++ b/server/api/controllers/show-config.js @@ -1,8 +1,26 @@ +const Errors = { + INVALID_OIDC_CONFIGURATION: { + invalidOidcConfiguration: 'Invalid OIDC configuration' + }, +}; + module.exports = { - fn() { + exits: { + invalidOidcConfiguration: { + responseType: 'serverError' + }, + }, + + async fn() { let oidc = null; if (sails.hooks.oidc.isActive()) { - const oidcClient = sails.hooks.oidc.getClient(); + let oidcClient; + try { + oidcClient = await sails.hooks.oidc.getClient(); + } catch (error) { + sails.log.warn(`Error while initializing OIDC client: ${error}`); + throw Errors.INVALID_OIDC_CONFIGURATION; + } const authorizationUrlParams = { scope: sails.config.custom.oidcScopes, diff --git a/server/api/helpers/users/get-or-create-one-using-oidc.js b/server/api/helpers/users/get-or-create-one-using-oidc.js index 2c3cb65f..5532c4d6 100644 --- a/server/api/helpers/users/get-or-create-one-using-oidc.js +++ b/server/api/helpers/users/get-or-create-one-using-oidc.js @@ -12,6 +12,7 @@ module.exports = { exits: { invalidCodeOrNonce: {}, + invalidOIDCConfiguration: {}, invalidUserinfoConfiguration: {}, missingValues: {}, emailAlreadyInUse: {}, @@ -19,7 +20,13 @@ module.exports = { }, async fn(inputs) { - const client = sails.hooks.oidc.getClient(); + let client; + try { + client = await sails.hooks.oidc.getClient(); + } catch (error) { + sails.log.warn(`Error while initializing OIDC client: ${error}`); + throw 'invalidOIDCConfiguration'; + } let tokenSet; try { diff --git a/server/api/hooks/oidc/index.js b/server/api/hooks/oidc/index.js index 47c2bf7a..73a670f4 100644 --- a/server/api/hooks/oidc/index.js +++ b/server/api/hooks/oidc/index.js @@ -15,37 +15,40 @@ module.exports = function defineOidcHook(sails) { /** * Runs when this Sails app loads/lifts. */ - async initialize() { - if (!sails.config.custom.oidcIssuer) { + if (!this.isActive()) { return; } sails.log.info('Initializing custom hook (`oidc`)'); - - const issuer = await openidClient.Issuer.discover(sails.config.custom.oidcIssuer); - - const metadata = { - client_id: sails.config.custom.oidcClientId, - client_secret: sails.config.custom.oidcClientSecret, - redirect_uris: [sails.config.custom.oidcRedirectUri], - response_types: ['code'], - userinfo_signed_response_alg: sails.config.custom.oidcUserinfoSignedResponseAlg, - }; - - if (sails.config.custom.oidcIdTokenSignedResponseAlg) { - metadata.id_token_signed_response_alg = sails.config.custom.oidcIdTokenSignedResponseAlg; - } - - client = new issuer.Client(metadata); }, - getClient() { + async getClient() { + if (client === null && this.isActive()) { + sails.log.info('Initializing OIDC client'); + + const issuer = await openidClient.Issuer.discover(sails.config.custom.oidcIssuer); + + const metadata = { + client_id: sails.config.custom.oidcClientId, + client_secret: sails.config.custom.oidcClientSecret, + redirect_uris: [sails.config.custom.oidcRedirectUri], + response_types: ['code'], + userinfo_signed_response_alg: sails.config.custom.oidcUserinfoSignedResponseAlg, + }; + + if (sails.config.custom.oidcIdTokenSignedResponseAlg) { + metadata.id_token_signed_response_alg = sails.config.custom.oidcIdTokenSignedResponseAlg; + } + + client = new issuer.Client(metadata); + } + return client; }, isActive() { - return client !== null; + return sails.config.custom.oidcIssuer !== undefined; }, }; };