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

799 lines (797 loc) 28.2 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.checkIfSubdomainIsReserved = exports.deleteTunnelsReservedUrl = exports.listTunnelsReservedUrl = exports.createTunnelsReservedUrl = exports.checkLiveProjectAndEnvironmentVersion = exports.acknowledgeShareLogs = exports.getShareLogs = exports.createShareLogs = exports.getTeamMateByCode = exports.teamMateSignup = exports.signup = exports.createSyncServer = exports.getTunnelsSubdomainStatus = exports.acknowlegdeActionLog = exports.getActionLogs = exports.createRecommendation = exports.createEnvironment = exports.createProject = exports.addSecrets = exports.updateSecret = exports.deleteSecret = exports.updateEnvironment = exports.getCurrentUser = exports.fetchProjectTeammates = exports.revokeAuthToken = exports.isUserOnline = exports.fetchProjects = exports.getCliEnvironment = exports.fetchSingleProject = exports.fetchSecrets = exports.generateAccessToken = exports.getAuthToken = exports.generateAuthCode = void 0; const axios_1 = require("axios"); const utils_1 = require("../utils"); const config_1 = require("../configuration/config"); const config_2 = require("../config"); const chalk = require("chalk"); const jwt_decode_1 = require("jwt-decode"); // TODO: Rewrite all the functions here const generateAuthCode = async (fingerprint, hostOS, hostName, hostARCH) => { var _a; const instance = config_1.default.getHttpInstance(); const query = `mutation { addAuthCode(addAuthCodeInput: {fingerprint: "${fingerprint}", hostOS: "${hostOS}", hostName: "${hostName}", hostARCH: "${hostARCH}"}) { pollingCode authCode hostOS hostName hostARCH } }`; const { data } = await instance.post("", { query }); if (data.errors) { console.error(chalk.bold.red(data.errors[0].message)); process.exit(1); } return (_a = data === null || data === void 0 ? void 0 : data.data) === null || _a === void 0 ? void 0 : _a.addAuthCode; }; exports.generateAuthCode = generateAuthCode; const getAuthToken = async (pollingCode) => { var _a; const instance = config_1.default.getHttpInstance(); const query = `query { verifyAuthCode(pollingCode: "${pollingCode}") { id token user { role { name id } id email name } } }`; const currentApiHost = instance.defaults.baseURL; config_1.default.setAuthApiHost(currentApiHost); try { const { data } = await instance.post("", { query }); return data; } catch (error) { if ((_a = error === null || error === void 0 ? void 0 : error.response) === null || _a === void 0 ? void 0 : _a.data) { console.log(error); } else console.log(error.message); process.exit(1); } }; exports.getAuthToken = getAuthToken; const generateAccessToken = async (authToken) => { var _a, _b, _c, _d, _e, _f, _g, _h, _j; const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); const { publicKey, privateKey } = (0, utils_1.generateRsaKeys)(); config_1.default.storeRsaKeys(publicKey, privateKey); const query = `mutation { authenticateToken(token: "${authToken}", frontendPublicKey: ${JSON.stringify(publicKey)}) { backendPublicKey accessToken authToken { serviceName project { title id } environment { title id } } user { email id name role { id name } } } }`; try { const { data } = await instance.post("", { query }); if (data.errors) { console.log(data.errors[0]); console.error(chalk.bold.red("An error occured while trying to generate Access Token. Pls login and try again.")); process.exit(1); } config_1.default.storeBackendPublicKey((_b = (_a = data === null || data === void 0 ? void 0 : data.data) === null || _a === void 0 ? void 0 : _a.authenticateToken) === null || _b === void 0 ? void 0 : _b.backendPublicKey); const { secretKey, team } = (0, jwt_decode_1.default)((_d = (_c = data === null || data === void 0 ? void 0 : data.data) === null || _c === void 0 ? void 0 : _c.authenticateToken) === null || _d === void 0 ? void 0 : _d.accessToken); /** * this secret key is encrypted with RSA so use the frontend * secret key to decrypt it to get the actual value */ const decryptedSecretKey = (0, utils_1.rsaDecryptSecret)(secretKey, config_1.default.getRsaKeys().privateKey); config_1.default.storeEncrytionSecretKey(decryptedSecretKey); const encryptionPassphrase = config_1.default.getEncryptionSecretKey(); return Object.assign((_e = data === null || data === void 0 ? void 0 : data.data) === null || _e === void 0 ? void 0 : _e.authenticateToken, { user: { name: await (0, utils_1.decryptPlainSecretAndReturnPlainValue)((_f = data === null || data === void 0 ? void 0 : data.data) === null || _f === void 0 ? void 0 : _f.authenticateToken.user.name, encryptionPassphrase), email: await (0, utils_1.decryptPlainSecretAndReturnPlainValue)((_g = data === null || data === void 0 ? void 0 : data.data) === null || _g === void 0 ? void 0 : _g.authenticateToken.user.email, encryptionPassphrase), id: await (0, utils_1.decryptPlainSecretAndReturnPlainValue)((_h = data === null || data === void 0 ? void 0 : data.data) === null || _h === void 0 ? void 0 : _h.authenticateToken.user.id, encryptionPassphrase), role: (_j = data === null || data === void 0 ? void 0 : data.data) === null || _j === void 0 ? void 0 : _j.authenticateToken.user.role, }, }); } catch (error) { console.error("An error occured. Pls try again."); process.exit(1); } }; exports.generateAccessToken = generateAccessToken; const fetchSecrets = async (project, environment, accessToken) => { var _a, _b, _c, _d; const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const environmentData = await (0, exports.getCliEnvironment)(project, environment, accessToken); const projects = await (0, exports.fetchProjects)(accessToken); const projectEnvironments = (_a = projects.find(({ title }) => title === project)) === null || _a === void 0 ? void 0 : _a.environments.list; const environmentId = (_b = projectEnvironments.find(({ title }) => title === environment)) === null || _b === void 0 ? void 0 : _b.id; const query = `query { generalSecrets( filterInput: { environmentId: "${environmentId}", fromCli: true }, take: ${Number(environmentData.totalSecrets)}, skip: 0 ) { list { id key keySha value comment member user { email } environment { id title member } project { id title member } mergeRequest { id comment } createdDate } } }`; const { data } = await instance.post("", { query }); if (data.errors && data.errors[0].message === "Unauthorized") { console.error(chalk.red("Sorry you don't have access to this project environment any longer, please contact admin")); process.exit(1); } if (data.errors) { const errorMessage = (_d = (_c = data.errors) === null || _c === void 0 ? void 0 : _c[0]) === null || _d === void 0 ? void 0 : _d.message; if (/upgrade your plan/gi.test(errorMessage)) { console.error(errorMessage); process.exit(1); } else console.log(errorMessage); } return data; }; exports.fetchSecrets = fetchSecrets; const fetchSingleProject = async (accessToken, project) => { const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `query { generalProjects(filterOptions: { title: "${project}", fromCli: true }) { list { id environments(take: 1000, skip: 0) { list { title id } } } } }`; const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); return data.data.generalProjects.list; }; exports.fetchSingleProject = fetchSingleProject; const getCliEnvironment = async (project, environment, accessToken) => { const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `query { getCliEnvironment(project: "${project}", environment: "${environment}") { totalSecrets } } `; const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); return data.data.getCliEnvironment; }; exports.getCliEnvironment = getCliEnvironment; const fetchProjects = async (accessToken) => { const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `query { generalProjects(filterOptions: { fromCli: true}, take: 1000, skip: 0) { list { id title member businessOwner { name email role { id name } } environments(take: 1000, skip: 0) { list { title id member } } } } }`; const { data } = await instance.post("", { query }); if (data.errors) { console.error(`There was an error fetching a list of your projects... Please run ${chalk.greenBright.bold("onboardbase login")} command again to be sure you have access to this organization.`); process.exit(1); } return data.data.generalProjects.list; }; exports.fetchProjects = fetchProjects; const isUserOnline = async () => { let isOnline = true; try { await axios_1.default.get("https://api.onboardbase.com/health"); } catch (error) { isOnline = false; } return isOnline; }; exports.isUserOnline = isUserOnline; const revokeAuthToken = async (token) => { var _a; const instance = config_1.default.getHttpInstance(); try { const query = `mutation { revokeAuthToken(token: "${token}") { status message } } `; const { data } = await instance.post("", { query }); return (_a = data === null || data === void 0 ? void 0 : data.data) === null || _a === void 0 ? void 0 : _a.revokeAuthToken; } catch (error) { // Silent error //console.log(chalk.bold.red("Could not revoke auth token")); } }; exports.revokeAuthToken = revokeAuthToken; const fetchProjectTeammates = async (project, accessToken) => { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `query { generalProjects(filterOptions: { title: "${project}", fromCli: true }) { list { team { users { list{ user { email id name } } } } } } }`; const { data } = await instance.post("", { query }); if (data.errors && data.errors[0].message === "Unauthorized") throw new Error(chalk.bold.red(data.errors[0].message)); return data; }; exports.fetchProjectTeammates = fetchProjectTeammates; const getCurrentUser = async (accessToken) => { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; console.log({ accessToken }); const decodedData = (0, jwt_decode_1.default)(accessToken); const query = `query { user(id: "${decodedData.sub}") { id name defaultTeam { id paymentTier { id tier } } teams { id team { name id } } } }`; const { data } = await instance.post("", { query }); if (data.errors) { console.error(chalk.bold.red(data.errors[0].message)); process.exit(1); } return data.data.user; }; exports.getCurrentUser = getCurrentUser; const updateEnvironment = async (accessToken, environmentId, secrets) => { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { updateEnvironment( updateEnvironmentInput: { key: ${JSON.stringify(`[${secrets}]`)}} environmentId: "${environmentId}" ) { id title } }`; const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); }; exports.updateEnvironment = updateEnvironment; const deleteSecret = async (accessToken, secretUUID) => { const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { deleteSecret(secretId: "${secretUUID}"){ id } }`; const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); }; exports.deleteSecret = deleteSecret; const updateSecret = async (accessToken, secretUUID, secretData) => { const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { updateSecret( secretId: "${secretUUID}" updateSecretInput: { key: "${secretData.key}", value: "${secretData.value}"} ){ id } }`; const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); }; exports.updateSecret = updateSecret; const addSecrets = async (accessToken, secrets) => { const instance = config_1.default.getHttpInstance(`${config_2.ConfigManager.CURRENT_SCOPE_API_HOST}/graphql`); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation addSecret ($addSecretsInput: [AddSecretInput!]!) { addSecrets(addSecretsInput: $addSecretsInput) { id key value url } }`; const variables = { addSecretsInput: secrets }; const { data } = await instance.post("", { query, variables }); if (data.errors) { if (data.errors[0].message === "Unauthorized") { throw new Error("Sorry you don't have access to this project environment any longer, please contact admin"); } else throw new Error(chalk.bold.red(data.errors[0].message)); } return data; }; exports.addSecrets = addSecrets; const createProject = async (accessToken, title, description, environment) => { var _a, _b; const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { addProject( addProjectInput: { title: "${title}" ${description ? `description: "${description}"` : ""} ${environment ? `environment: "${environment}"` : ""} type: "api_keys" } ) { id } } `; try { const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); } catch (error) { if ((error === null || error === void 0 ? void 0 : error.response) && ((_a = error === null || error === void 0 ? void 0 : error.response) === null || _a === void 0 ? void 0 : _a.data)) { console.error(chalk.bold.red((_b = error === null || error === void 0 ? void 0 : error.response) === null || _b === void 0 ? void 0 : _b.data)); process.exit(1); } console.error(error); process.exit(1); } }; exports.createProject = createProject; const createEnvironment = async (accessToken, project, environment) => { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { addEnvironment( addEnvironmentInput: { project: "${project}", title: "${environment}" } ) { title id } }`; try { const { data } = await instance.post("", { query }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); return data.data.addEnvironment; } catch (error) { console.log("Error:", chalk.red(error.message)); process.exit(1); } }; exports.createEnvironment = createEnvironment; const createRecommendation = async (accessToken, environmentId, secrets, comment) => { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation addMergeRequest ($addSecretsInput: [BaseAddSecretInput!]) { addMergeRequest(addMergeRequestInput: { environmentId: "${environmentId}", comment: "${comment}", secrets: $addSecretsInput }) { comment } }`; const variables = { addSecretsInput: [secrets], }; const { data } = await instance.post("", { query, variables }); if (data.errors) throw new Error(chalk.bold.red(data.errors[0].message)); }; exports.createRecommendation = createRecommendation; const getActionLogs = async (userEmail, teamId) => { const instance = config_1.default.getHttpInstance(); const query = `{ getActionTables( userEmail: "${userEmail}" teamId: "${teamId}" ) { list { id action executed } } }`; try { const { data } = await instance.post("", { query, }); if (data.errors) { console.error(data.errors[0]); console.error("FETCHING ACTION TABLES ERROR --->", chalk.bold.red(data.errors[0].message)); process.exit(1); } return data; } catch (error) { console.error("FETCHING ACTION TABLES ERROR --->", error.message); process.exit(1); } }; exports.getActionLogs = getActionLogs; const acknowlegdeActionLog = async (actionTableId) => { const instance = config_1.default.getHttpInstance(); const query = `mutation { updateActionTable(actionTableId: "${actionTableId}") }`; try { const { data } = await instance.post("", { query }); if (data.errors) { console.error("ERROR UPDATING ACTION TABLE --->", chalk.bold.red(data.errors[0].message)); process.exit(1); } } catch (error) { console.error("ERROR UPDATING ACTION TABLE --->", error.message); process.exit(1); } }; exports.acknowlegdeActionLog = acknowlegdeActionLog; const getTunnelsSubdomainStatus = async (subdomain) => { let subdomainHasBeenUsed; try { await axios_1.default.get(`https://tunnels.onboardbase.com/api/tunnels/${subdomain}/status`); subdomainHasBeenUsed = true; } catch (error) { if (error.response.status === 404) { subdomainHasBeenUsed = false; } } return subdomainHasBeenUsed; }; exports.getTunnelsSubdomainStatus = getTunnelsSubdomainStatus; const createSyncServer = async (payload) => { try { const syncServerUrl = "https://sync-socket-server.onboardbase.com/servers/create"; const { data } = await axios_1.default.post(syncServerUrl, payload); return data; } catch (error) { // silently kill the error } }; exports.createSyncServer = createSyncServer; const signup = async (data) => { const instance = config_1.default.getHttpInstance(); const query = `mutation { signup(registrationInput: {email: "${data.email}", teamName: "${data.teamName}", name: "${data.name}", cliSignUpAuthCode: "${data.authCode}"}) { backendPublicKey } }`; try { const { data } = await instance.post("", { query }); if (data.errors) { console.log(chalk.bold.red(data.errors[0].message)); process.exit(0); } return data; } catch (error) { console.error(error); process.exit(1); } }; exports.signup = signup; const teamMateSignup = async (data) => { const instance = config_1.default.getHttpInstance(); const query = `mutation { setupNewEmployeeProfile(id: "${data.userId}", authCode: "${data.authCode}", fromNonBrowserEnvironment: true, userInput: {name: "${data.name}", confirmationCode: "${data.confirmationCode}"}) { accessToken } }`; try { const { data } = await instance.post("", { query }); if (data.errors) { throw new Error(data.errors[0].message); } return data; } catch (error) { console.error(error); } }; exports.teamMateSignup = teamMateSignup; const getTeamMateByCode = async (code) => { const instance = config_1.default.getHttpInstance(); const query = `query { newEmployee(confirmationCode: "${code}") { id teamName } }`; try { const { data } = await instance.post("", { query }); if (data.errors) { throw new Error(chalk.bold.red(data.errors[0].message)); } return data.data.newEmployee.id; } catch (error) { console.error(error.message); process.exit(1); } }; exports.getTeamMateByCode = getTeamMateByCode; const createShareLogs = async ({ receiverId, receiverEmail, senderId, senderEmail, secrets, accessToken, }) => { var _a, _b; try { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation createShareLogs($createShareLogInput: CreateShareLogsInput!){ createShareLogs(createShareLogInput: $createShareLogInput) { id } }`; const variables = { senderEmail, senderId, receiverEmail, receiverId, secrets, }; const { data } = await instance.post("", { query, variables: { createShareLogInput: variables }, }); if (data.errors) { throw new Error(chalk.bold.red(data.errors[0].message)); } return (_b = (_a = data === null || data === void 0 ? void 0 : data.data) === null || _a === void 0 ? void 0 : _a.createShareLogs) === null || _b === void 0 ? void 0 : _b.id; } catch (error) { } }; exports.createShareLogs = createShareLogs; const getShareLogs = async (userId) => { try { const instance = config_1.default.getHttpInstance(); const query = `query { findShareLogsByReceiverEmailOrId(receiver: "${userId}"){ id secrets } }`; const { data } = await instance.post("", { query }); if (data.errors) { throw new Error(chalk.bold.red(data.errors[0].message)); } return data.data.findShareLogsByReceiverEmailOrId; } catch (error) { } }; exports.getShareLogs = getShareLogs; const acknowledgeShareLogs = async (shareLogId) => { try { const instance = config_1.default.getHttpInstance(); const query = `mutation { updateShareLogStatus(shareId: "${shareLogId}", ack: true){ id } }`; const { data } = await instance.post("", { query }); if (data.errors) { throw new Error(chalk.bold.red(data.errors[0].message)); } } catch (error) { } }; exports.acknowledgeShareLogs = acknowledgeShareLogs; const checkLiveProjectAndEnvironmentVersion = async (project, environment, token) => { try { const instance = config_1.default.getHttpInstance(); const query = `query { getEnvironmentVersion( token: "${token}", project: "${project}", environment: "${environment}" ) { version } }`; const { data } = await instance.post("", { query }); if (data.errors) { throw new Error(chalk.bold.red(data.errors[0].message)); } return parseInt(data.data.getEnvironmentVersion.version); } catch (error) { throw new Error(error === null || error === void 0 ? void 0 : error.message); } }; exports.checkLiveProjectAndEnvironmentVersion = checkLiveProjectAndEnvironmentVersion; const createTunnelsReservedUrl = async (url, accessToken) => { try { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { createReservedTunnelUrls( createReservedTunnelUrlsInput: { subDomain: "${url}" } ) { subDomain id } }`; const { data } = await instance.post("", { query }); if (data.errors) { console.error(chalk.bold.red(data.errors[0].message)); process.exit(1); } } catch (error) { console.log(error); } }; exports.createTunnelsReservedUrl = createTunnelsReservedUrl; const listTunnelsReservedUrl = async (accessToken) => { try { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `query { getAllReservedTunnelUrls { id disabled subDomain } }`; const { data } = await instance.post("", { query }); if (data.errors) { throw new Error(chalk.bold.red(data.errors[0].message)); } return data.data.getAllReservedTunnelUrls; } catch (error) { console.log(error); } }; exports.listTunnelsReservedUrl = listTunnelsReservedUrl; const deleteTunnelsReservedUrl = async (accessToken, tunnelUrlId) => { try { const instance = config_1.default.getHttpInstance(); instance.defaults.headers["Authorization"] = `Bearer ${accessToken}`; const query = `mutation { disableReservedTunnelUrls(tunnelUrlId: "${tunnelUrlId}") { isSuccess } }`; const { data } = await instance.post("", { query }); if (data.errors) { console.error(chalk.bold.red(data.errors[0].message)); process.exit(1); } return data.data.disableReservedTunnelUrls.isSuccess; } catch (error) { console.log(error); } }; exports.deleteTunnelsReservedUrl = deleteTunnelsReservedUrl; const checkIfSubdomainIsReserved = async (subdomain) => { try { const instance = config_1.default.getHttpInstance(); const query = `query { checkIfSubDomainIsReserved(subDomain: "${subdomain}") { isReserved } }`; const { data } = await instance.post("", { query }); if (data.errors) { console.error(chalk.bold.red(data.errors[0].message)); process.exit(1); } return data.data.checkIfSubDomainIsReserved.isReserved; } catch (error) { console.log(error); } }; exports.checkIfSubdomainIsReserved = checkIfSubdomainIsReserved;