zcatalyst-cli
Version:
Command Line Tool for CATALYST
300 lines (299 loc) • 13.3 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
__setModuleDefault(result, mod);
return result;
};
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 };
};
Object.defineProperty(exports, "__esModule", { value: true });
const command_1 = __importDefault(require("../../../internal/command"));
const constants_1 = require("../../../util_modules/constants");
const prompt_1 = __importDefault(require("../../../prompt"));
const js_1 = require("../../../util_modules/js");
const endpoints_1 = require("../../../endpoints");
const runtime_store_1 = __importDefault(require("../../../runtime-store"));
const archiver_1 = __importDefault(require("../../../archiver"));
const logger_1 = require("../../../util_modules/logger");
const inquirer_1 = __importStar(require("inquirer"));
const error_1 = __importDefault(require("../../../error"));
const project_1 = require("../../../util_modules/project");
const features_1 = require("../../../init/features");
const path_1 = require("path");
const throbber_1 = __importDefault(require("../../../throbber"));
const config_1 = require("../../../util_modules/config");
const common_1 = require("../../../init/util/common");
const ansi_colors_1 = require("ansi-colors");
const fs_1 = require("../../../util_modules/fs");
const console_1 = require("console");
function getSpecification(specs = []) {
return __awaiter(this, void 0, void 0, function* () {
const res = (yield (yield (0, endpoints_1.zestAPI)()).getSpecifications());
if (!res) {
return specs;
}
specs.push(...res.specifications);
if (res.info.more_records) {
yield getSpecification(specs);
}
return specs;
});
}
function searchSpecification(filter, specArray = []) {
return __awaiter(this, void 0, void 0, function* () {
if (filter) {
const response = [];
specArray.forEach((spec) => {
if (spec.name.includes(filter)) {
response.push(spec);
}
});
return response;
}
return specArray;
});
}
function pollScheduledJob(job_id) {
return __awaiter(this, void 0, void 0, function* () {
const throbber = throbber_1.default.getInstance();
try {
const res = (yield (yield (0, endpoints_1.zestAPI)()).getScheduledJob(job_id));
const status = js_1.JS.capitalize(res.scheduled_jobs[0].status);
if (status === 'Completed') {
throbber.succeed('processing', { text: `Status >> ${status}` });
return res;
}
throbber.add('processing', { text: `Status >> ${status}` });
if (status === 'Failed') {
throbber.fail('processing', { text: `Status >> ${status}` });
throw new error_1.default('zest generation failed', {
exit: 2,
original: `${res.scheduled_jobs[0].action_info.failure_reason}`
});
}
yield js_1.JS.sleep(1000);
}
catch (err) {
throw new error_1.default('Error while processing scheduled job', {
exit: 2,
original: err
});
}
return yield pollScheduledJob(job_id);
});
}
function downloadSourceCode(fileId, outputDir, srcType, srcName) {
return __awaiter(this, void 0, void 0, function* () {
const zestZip = (yield (yield (0, endpoints_1.zestAPI)()).getFile(fileId, srcType, srcName));
yield new archiver_1.default().load(zestZip).extract(outputDir).finalize();
});
}
exports.default = new command_1.default('zest:generate')
.description('Generate the functions or appsail source code for your ZEST Specifications')
.needs('auth', [])
.needs('config', { optional: true })
.needs('rc', { skipOrgCheck: false })
.action(() => __awaiter(void 0, void 0, void 0, function* () {
var _a;
const specArray = yield getSpecification();
if (specArray.length === 0) {
throw new error_1.default('No Specifications Found', {
exit: 1,
errorId: 'ZEST-GEN-1'
});
}
yield prompt_1.default.register('search-box');
const specName = yield inquirer_1.default.prompt([
{
type: 'search-box',
name: 'specs',
searchable: true,
pageSize: 10,
highlight: true,
notFoundMsg: 'No specifications found!',
searchMsg: 'Search specifications...',
message: 'Please search and select the specifications(Use space key to select)',
source(_answersSoFar, input) {
input || (input = '');
return new Promise((resolve) => __awaiter(this, void 0, void 0, function* () {
const fuzzyResult = yield searchSpecification(input, specArray);
const data = fuzzyResult.map((element) => {
return {
name: `${element.name}(${element.version})`,
value: element.id
};
});
resolve(data);
}));
},
validate: (ansArr) => {
if (js_1.JS.isEmpty(ansArr)) {
return 'Must select one specification.';
}
return true;
}
}
]);
const srcTypeAns = yield prompt_1.default.ask(prompt_1.default.question('source', 'Please specify which source type you want to download', {
type: 'list',
choices: [
prompt_1.default.choice('Function', {
value: 'functions'
}),
prompt_1.default.choice('AppSail', {
value: 'appsail'
})
]
}));
const srcType = srcTypeAns.source;
const sourceLabel = srcType.replace('functions', 'function');
const runtimeChoices = yield (0, common_1.getRuntimeChoices)({ fnType: 'aio' });
const ignoreRuntimes = ['node14', 'node12', 'node20'];
const stackChoices = runtimeChoices.filter((choice) => {
if (!(choice instanceof inquirer_1.Separator)) {
return !ignoreRuntimes.includes(choice.value.runtime);
}
return choice;
});
const srcStackAns = yield prompt_1.default.ask(prompt_1.default.question('stack', `Please select the language for your ${sourceLabel}`, {
type: 'list',
choices: stackChoices.map((choice) => {
if (!(choice instanceof inquirer_1.Separator)) {
return choice;
}
return choice;
}),
when: () => {
return runtimeChoices.length > 1;
}
}));
const srcStack = srcStackAns.stack.runtime;
const existingSails = config_1.appSailConfig.raw() || [];
const existingFuncs = ((_a = config_1.functionsConfig.raw()) === null || _a === void 0 ? void 0 : _a.targets) || [];
const source = yield prompt_1.default.ask(prompt_1.default.question('name', `Please provide a name for your ${(0, ansi_colors_1.bold)(sourceLabel)} `, {
type: 'input',
default: 'sample',
validate: (input) => __awaiter(void 0, void 0, void 0, function* () {
if (input === '') {
return 'Please provide a valid name.';
}
if (input === '' || !input.match(constants_1.REGEX.functions.package.name)) {
return `Special characters are not allowed. Includes only alphabets, numbers, hyphen and underscores.`;
}
if (srcType === 'functions' &&
existingFuncs.findIndex((func) => func === input) !== -1) {
return 'function name already exists';
}
if (srcType === 'appsail' &&
existingSails.findIndex((appSail) => appSail.name === input) !== -1) {
return 'appsail name already exists';
}
return true;
})
}));
const srcName = source.name;
let sourceCodeRes;
const resources = [];
specName.specs.forEach((element) => {
resources.push({ id: element });
});
const config = runtime_store_1.default.get('config');
let payload, outputDir;
if (srcType === 'appsail') {
const generateAppsailParams = {
resources: resources,
stack: srcStack,
name: srcName
};
outputDir = (0, project_1.resolveProjectPath)(`appsail-${srcName}`);
payload = {
source: outputDir,
name: srcName
};
if (srcStackAns.stack.lang.startsWith('java')) {
const basePackage = yield prompt_1.default.ask(prompt_1.default.question('basePkg', 'Please specify the base package name', {
type: 'input',
default: 'com.zoho'
}));
const install = yield prompt_1.default.ask(prompt_1.default.question('consent', 'Do you wish to install dependencies ? ', {
type: 'confirm',
default: true
}));
Object.assign(generateAppsailParams, {
with_dependency: install.consent,
config: {
base_package: basePackage.basePkg
}
});
}
sourceCodeRes = yield (yield (0, endpoints_1.zestAPI)()).generateAppsail(generateAppsailParams);
}
else {
const functionsDirPath = (0, project_1.resolveProjectPath)(config.get('functions.source') || constants_1.FOLDERNAME.functions);
outputDir = (0, path_1.join)(functionsDirPath, srcName);
payload = {
source: outputDir,
name: srcName,
stack: srcStack,
type: 'aio'
};
sourceCodeRes = yield (yield (0, endpoints_1.zestAPI)()).generateFunction(resources, srcStack, srcName);
}
const folderExists = yield fs_1.ASYNC.dirExists(outputDir);
const overwriteAns = folderExists
? yield prompt_1.default.ask(prompt_1.default.question('overwrite', 'Directory ' + (0, ansi_colors_1.underline)(outputDir) + ' already exists. Overwrite ?', {
type: 'confirm',
defaultAns: false
}))
: { overwrite: true };
if (!overwriteAns.overwrite) {
(0, logger_1.labeled)('zest', `${sourceLabel} generation skipped.`).WARN();
return;
}
yield fs_1.ASYNC.deleteDir(outputDir);
runtime_store_1.default.set(`payload.${srcType}.targets`, [payload]);
const job_id = sourceCodeRes.job_id;
const throbber = throbber_1.default.getInstance();
(0, console_1.info)('\n' + (0, ansi_colors_1.white)('==> ') + `Generating ${js_1.JS.capitalize(sourceLabel)}`);
const fileId = yield pollScheduledJob(job_id).then((data) => {
throbber.remove('processing');
return data.scheduled_jobs[0].action_info.file_id;
});
(0, console_1.info)('\n' + (0, ansi_colors_1.white)('==> ') + `Downloading ${js_1.JS.capitalize(sourceLabel)}`);
yield downloadSourceCode(fileId, outputDir, sourceLabel, srcName);
(0, features_1.setCatalystConfig)(srcType, true);
yield config.save();
(0, console_1.info)();
(0, logger_1.message)((0, ansi_colors_1.bold)(constants_1.FILENAME.config) +
` file has been successfully updated with ${sourceLabel} details.`);
(0, console_1.info)();
(0, logger_1.success)(`Zest successfully generated in ${(0, ansi_colors_1.bold)((0, path_1.join)(outputDir))}.`);
}));