UNPKG

@onboardbase/cli

Version:

[![Version](https://img.shields.io/npm/v/@onboardbase/cli.svg)](https://www.npmjs.com/package/@onboardbase/cli) [![Downloads/week](https://img.shields.io/npm/dw/@onboardbase/cli.svg)](https://www.npmjs.com/package/@onboardbase/cli) [![License](https://img

150 lines (149 loc) 7.34 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.AccessManager = void 0; const jwt_decode_1 = require("jwt-decode"); const base_service_1 = require("../../common/base.service"); const crypto_1 = require("../../common/utils/crypto"); const http_service_1 = require("../../common/http.service"); const types_1 = require("../../common/types"); const chalk = require("chalk"); const errors_1 = require("../../common/errors"); const types_2 = require("./types"); class AccessManager extends base_service_1.BaseService { constructor(configManager) { super(configManager); http_service_1.HTTPService.instance.interceptors.response.use(async (response) => { var _a, _b; const errors = (_a = response === null || response === void 0 ? void 0 : response.data) === null || _a === void 0 ? void 0 : _a.errors; if (!errors) return response; const isUnauthorized = (_b = errors[0].message) === null || _b === void 0 ? void 0 : _b.includes("Unauthorized"); if (isUnauthorized) { const { accessToken } = await this.refreshAccessToken(); response.config.headers["Authorization"] = `Bearer ${accessToken}`; return http_service_1.HTTPService.instance.request(response.config); } return response; }); } decodeAccessToken(accToken) { return (0, jwt_decode_1.default)(accToken); } getSecretKeyFromAccessToken(accessToken, privateKey) { const { secretKey } = this.decodeAccessToken(accessToken); return (0, crypto_1.rsaDecryptCipherText)({ cipherText: secretKey, privateKey }); } getRSAKeys() { const rsaKeys = this.configManager.getRSAKeys(); if (rsaKeys) return rsaKeys; const { publicKey, privateKey } = (0, crypto_1.generateRsaKeys)(); this.configManager.setRSAKeys({ publicKey, privateKey }); return { publicKey, privateKey }; } async _generateAccessToken(deviceToken) { const { publicKey, privateKey } = this.getRSAKeys(); const accessTokenResult = await this.httpInstance.getAuthInfoFromDeviceToken({ token: deviceToken, publicKey, }); // cache this const plainSecretKey = await this.getSecretKeyFromAccessToken(accessTokenResult === null || accessTokenResult === void 0 ? void 0 : accessTokenResult.accessToken, privateKey); return Object.assign(accessTokenResult, { user: { name: await (0, crypto_1.decryptCipherText)({ cipherText: accessTokenResult.user.name, passphrase: plainSecretKey, }), email: await (0, crypto_1.decryptCipherText)({ cipherText: accessTokenResult.user.email, passphrase: plainSecretKey, }), id: await (0, crypto_1.decryptCipherText)({ cipherText: accessTokenResult.user.id, passphrase: plainSecretKey, }), role: accessTokenResult.user.role, }, }, { secretKey: plainSecretKey, }); } async getAuthInfo() { const cachedAuthResult = this.getConfigForCurrentScope("auth-result"); if (cachedAuthResult && cachedAuthResult.accessToken) return cachedAuthResult; const deviceToken = this._getFromGlobalConfigOrThrow({ configPath: "token", envName: types_1.ENV_NAMES.TOKEN, }); const authResult = await this._generateAccessToken(deviceToken); this.setScopeConfig("auth-result", Object.assign({}, authResult)); return authResult; } async getAuthInfoFromDeviceToken(deviceToken) { const cachedAuthResult = this.getConfigForCurrentScope("auth-result"); if (cachedAuthResult && cachedAuthResult.accessToken) return cachedAuthResult; const authResult = await this._generateAccessToken(deviceToken); this.setScopeConfig("auth-result", Object.assign({}, authResult)); return authResult; } async refreshAccessToken() { const deviceToken = this.getConfigForCurrentScope("token"); const authResult = await this._generateAccessToken(deviceToken); this.setScopeConfig("auth-result", Object.assign(Object.assign({}, authResult), { pulled: true })); return authResult; } async checkUserAccess(deviceToken, project, environment) { const { accessToken } = await this.getAuthInfoFromDeviceToken(deviceToken); const { remoteEnvironment } = await this._throwIfProjectEnvironmentNotExist(accessToken, project, environment); this.setScopeConfig(`environment-id`, remoteEnvironment.id); return remoteEnvironment.member; } async _throwIfProjectEnvironmentNotExist(accessToken, project, environment) { const remoteProjects = await this.httpInstance.fetchProjects(accessToken); const remoteProject = remoteProjects.find(({ title }) => project === title); if (!remoteProject) { throw errors_1.BadConfigError.from(`Project does not exists`); } const remoteEnvironment = remoteProject.environments.list.find(({ title }) => environment === title); if (!remoteEnvironment) { throw errors_1.BadConfigError.from(`Environment does not exist under project`); } return { remoteEnvironment, remoteProject }; } async handleUserAdminPrivileges(projectName) { const userHasAdminPriviledges = await this._checkIfUserHasAdminPrivileges(); if (!userHasAdminPriviledges) { if (projectName) { let isProjectAdmin = await this._checkIfUserHasProjectAdminPrivileges(projectName); if (isProjectAdmin) return; } console.log(chalk.red(`You don't have admin privileges for this project, please contact the project owner to download secrets`)); throw new errors_1.BadInputError(`Unauthorized access`); } } async _checkIfUserHasAdminPrivileges() { var _a; let cachedAuthResult = await this.getAuthInfo(); if (!cachedAuthResult) { console.log(chalk.red(`You are not logged in, please run 'onboardbase login' to login`)); throw new errors_1.BadInputError(`Unauthorized access`); } const accessToken = cachedAuthResult.accessToken; const token = (0, jwt_decode_1.default)(accessToken); const userHasAdminPriviledges = ((_a = token.teamRole) === null || _a === void 0 ? void 0 : _a.name) !== types_2.TeamRole.EMPLOYEE; return userHasAdminPriviledges; } async _checkIfUserHasProjectAdminPrivileges(projectName) { let cachedAuthResult = await this.getAuthInfo(); if (!cachedAuthResult) { console.log(chalk.red(`You are not logged in, please run 'onboardbase login' to login`)); throw new errors_1.BadInputError(`Unauthorized access`); } const result = this.httpInstance.checkProjectAccess(cachedAuthResult.accessToken, projectName); return result; } } exports.AccessManager = AccessManager;