UNPKG

@sphereon/ssi-express-support

Version:

214 lines • 11.6 kB
"use strict"; var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; var _a; Object.defineProperty(exports, "__esModule", { value: true }); exports.OpenIDConnectAuthApi = void 0; exports.oidcDiscoverIssuer = oidcDiscoverIssuer; exports.oidcGetClient = oidcGetClient; exports.getLoginEndpoint = getLoginEndpoint; exports.getLoginCallbackEndpoint = getLoginCallbackEndpoint; exports.getLogoutEndpoint = getLogoutEndpoint; exports.getLogoutCallbackEndpoint = getLogoutCallbackEndpoint; exports.getIdTokenEndpoint = getIdTokenEndpoint; exports.getAuthenticatedUserEndpoint = getAuthenticatedUserEndpoint; const express_1 = __importDefault(require("express")); const openid_client_1 = require("openid-client"); const passport_1 = __importDefault(require("passport")); const auth_utils_1 = require("./auth-utils"); const express_utils_1 = require("./express-utils"); const functions_1 = require("./functions"); const PREFIX = (_a = process.env.PREFIX) !== null && _a !== void 0 ? _a : ''; function oidcDiscoverIssuer(opts) { return __awaiter(this, void 0, void 0, function* () { var _a, _b; const issuerUrl = (_b = (_a = opts === null || opts === void 0 ? void 0 : opts.issuerUrl) !== null && _a !== void 0 ? _a : (0, functions_1.env)('OIDC_ISSUER', PREFIX)) !== null && _b !== void 0 ? _b : 'https://auth01.test.sphereon.com/auth/realms/energy-shr'; const issuer = yield openid_client_1.Issuer.discover(issuerUrl); console.log('Discovered issuer %s %O', issuer.issuer, issuer.metadata); return { issuer, issuerUrl }; }); } function oidcGetClient(issuer, metadata, opts) { return __awaiter(this, void 0, void 0, function* () { // @ts-ignore return new issuer.Client(metadata, opts === null || opts === void 0 ? void 0 : opts.jwks, opts === null || opts === void 0 ? void 0 : opts.options); }); } function getLoginEndpoint(router, opts) { var _a, _b, _c, _d, _e, _f; if ((opts === null || opts === void 0 ? void 0 : opts.enabled) === false) { console.log(`Login endpoint is disabled`); return; } const strategy = (_b = (_a = opts === null || opts === void 0 ? void 0 : opts.endpoint) === null || _a === void 0 ? void 0 : _a.authentication) === null || _b === void 0 ? void 0 : _b.strategy; if (!strategy) { throw Error('strategy needs to be provided'); } const path = (_c = opts === null || opts === void 0 ? void 0 : opts.path) !== null && _c !== void 0 ? _c : '/authentication/login'; router.get(path, (req, res, next) => { var _a; const redirectPage = (_a = req.get('referer')) !== null && _a !== void 0 ? _a : '/'; req.session.redirectPage = redirectPage; next(); }, passport_1.default.authenticate(strategy, Object.assign(Object.assign(Object.assign({}, (_d = opts.authentication) === null || _d === void 0 ? void 0 : _d.strategyOptions), (_f = (_e = opts.endpoint) === null || _e === void 0 ? void 0 : _e.authentication) === null || _f === void 0 ? void 0 : _f.strategyOptions), { keepSessionInfo: false }), undefined)); } function getLoginCallbackEndpoint(router, opts) { var _a, _b, _c, _d, _e, _f; if ((opts === null || opts === void 0 ? void 0 : opts.enabled) === false) { console.log(`Auth callback endpoint is disabled`); return; } const strategy = (_b = (_a = opts === null || opts === void 0 ? void 0 : opts.endpoint) === null || _a === void 0 ? void 0 : _a.authentication) === null || _b === void 0 ? void 0 : _b.strategy; if (!strategy) { throw Error('strategy needs to be provided'); } const path = (_c = opts === null || opts === void 0 ? void 0 : opts.path) !== null && _c !== void 0 ? _c : '/authentication/callback'; router.get(path, passport_1.default.authenticate(strategy, Object.assign(Object.assign(Object.assign({}, (_d = opts.authentication) === null || _d === void 0 ? void 0 : _d.strategyOptions), (_f = (_e = opts.endpoint) === null || _e === void 0 ? void 0 : _e.authentication) === null || _f === void 0 ? void 0 : _f.strategyOptions), { keepSessionInfo: true }), undefined), (req, res, next) => { var _a, _b, _c; if (req.user) { console.log('User authenticated', (_a = req.user) === null || _a === void 0 ? void 0 : _a.name); // console.log(req.session) const redirectPage = (_b = req.session.redirectPage) !== null && _b !== void 0 ? _b : '/search'; // console.log(`PRE LOGIN PAGE in callback: ${redirectPage}`) delete req.session.redirectPage; return res.redirect(redirectPage); } else { return res.redirect((_c = (0, functions_1.env)('OIDC_FRONTEND_LOGIN_URL', PREFIX)) !== null && _c !== void 0 ? _c : 'http://localhost:3001/authentication/login'); } }); } function getLogoutEndpoint(router, client, opts) { var _a; if ((opts === null || opts === void 0 ? void 0 : opts.enabled) === false) { console.log(`Logout endpoint is disabled`); return; } const path = (_a = opts === null || opts === void 0 ? void 0 : opts.path) !== null && _a !== void 0 ? _a : '/authentication/logout'; router.get(path, (req, res) => { try { if (client.endSessionUrl()) { return res.redirect(client.endSessionUrl()); } else { console.log('IDP does not support end session url'); return res.redirect('/authentication/logout-callback'); } } catch (error) { console.log(error); return res.redirect('/authentication/logout-callback'); } }); } function getLogoutCallbackEndpoint(router, opts) { var _a; if ((opts === null || opts === void 0 ? void 0 : opts.enabled) === false) { console.log(`Logout callback endpoint is disabled`); return; } const path = (_a = opts === null || opts === void 0 ? void 0 : opts.path) !== null && _a !== void 0 ? _a : '/authentication/logout-callback'; router.get(path, (req, res, next) => { var _a; try { req.logout((err) => { if (err) { console.log(`Error during calling logout-callback: ${JSON.stringify(err)}`); } }); return res.redirect((_a = (0, functions_1.env)('OIDC_FRONTEND_LOGOUT_REDIRECT_URL', PREFIX)) !== null && _a !== void 0 ? _a : '/'); } catch (e) { return (0, express_utils_1.sendErrorResponse)(res, 500, 'An unexpected error occurred during logout callback', e); } }); } function getIdTokenEndpoint(router, client, opts) { var _a; if ((opts === null || opts === void 0 ? void 0 : opts.enabled) === false) { console.log(`ID Token endpoint is disabled`); return; } const path = (_a = opts.path) !== null && _a !== void 0 ? _a : '/authentication/tokens/id'; router.get(path, auth_utils_1.isUserAuthenticated, (req, res) => { if (req.session.tokens.id_token) { return res.json({ id_token: req.session.tokens.id_token }); } else { return (0, express_utils_1.sendErrorResponse)(res, 401, 'Authentication required'); } }); } function getAuthenticatedUserEndpoint(router, opts) { var _a; if ((opts === null || opts === void 0 ? void 0 : opts.enabled) === false) { console.log(`Authenticated User endpoint is disabled`); return; } const path = (_a = opts === null || opts === void 0 ? void 0 : opts.path) !== null && _a !== void 0 ? _a : '/authentication/user'; router.get(path, auth_utils_1.isUserAuthenticated, (req, res, next) => { if (!req.user) { return (0, express_utils_1.sendErrorResponse)(res, 401, 'Authentication required'); } let user = req.user; return res.json(user); }); } class OpenIDConnectAuthApi { get router() { return this._router; } constructor(args) { var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k; const { agent, opts } = args; this._agent = agent; (0, auth_utils_1.copyGlobalAuthToEndpoints)({ opts, keys: ['getLogin'] }); (0, auth_utils_1.copyGlobalAuthToEndpoints)({ opts, keys: ['getIdToken'] }); (0, auth_utils_1.copyGlobalAuthToEndpoints)({ opts, keys: ['getAuthenticatedUser'] }); // no need for the logout, as you these are not protected by auth this._opts = opts; this._express = args.expressSupport.express; this._router = express_1.default.Router(); const features = (_a = opts === null || opts === void 0 ? void 0 : opts.enabledFeatures) !== null && _a !== void 0 ? _a : ['login', 'logout', 'id-token', 'authenticated-user']; console.log(`Authentication API enabled`); if (features.includes('login')) { getLoginEndpoint(this.router, (_b = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _b === void 0 ? void 0 : _b.getLogin); getLoginCallbackEndpoint(this.router, (_c = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _c === void 0 ? void 0 : _c.getLogin); } if (features.includes('logout')) { getLogoutEndpoint(this.router, args.client, (_d = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _d === void 0 ? void 0 : _d.getLogout); getLogoutCallbackEndpoint(this.router, (_e = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _e === void 0 ? void 0 : _e.getLogout); } if (features.includes('id-token')) { if (((_f = opts.endpointOpts) === null || _f === void 0 ? void 0 : _f.getIdToken) === undefined) { throw Error('Cannot enable id-token endpoint without providing id-token endpoint options'); } getIdTokenEndpoint(this.router, args.client, (_g = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _g === void 0 ? void 0 : _g.getIdToken); } if (features.includes('authenticated-user')) { getAuthenticatedUserEndpoint(this.router, (_h = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _h === void 0 ? void 0 : _h.getAuthenticatedUser); } this._express.use((_k = (_j = opts === null || opts === void 0 ? void 0 : opts.endpointOpts) === null || _j === void 0 ? void 0 : _j.basePath) !== null && _k !== void 0 ? _k : '', this.router); } get agent() { return this._agent; } get opts() { return this._opts; } get express() { return this._express; } } exports.OpenIDConnectAuthApi = OpenIDConnectAuthApi; //# sourceMappingURL=openid-connect-rp.js.map