UNPKG

@ionic/cli-utils

Version:
190 lines (189 loc) 7.48 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); const tslib_1 = require("tslib"); const cli_framework_1 = require("@ionic/cli-framework"); const chalk_1 = require("chalk"); const Debug = require("debug"); const errors_1 = require("./errors"); const hooks_1 = require("./hooks"); const debug = Debug('ionic:cli-utils:lib:build'); exports.BUILD_SCRIPT = 'ionic:build'; exports.COMMON_BUILD_COMMAND_OPTIONS = [ { name: 'engine', summary: `Target engine (e.g. ${['browser', 'cordova'].map(e => chalk_1.default.green(e)).join(', ')})`, groups: [cli_framework_1.OptionGroup.Advanced], }, { name: 'platform', summary: `Target platform on chosen engine (e.g. ${['ios', 'android'].map(e => chalk_1.default.green(e)).join(', ')})`, groups: [cli_framework_1.OptionGroup.Advanced], }, ]; class BuildRunner { createBaseOptionsFromCommandLine(inputs, options) { const separatedArgs = options['--']; const platform = options['platform'] ? String(options['platform']) : undefined; const engine = this.determineEngineFromCommandLine(options); const project = options['project'] ? String(options['project']) : undefined; return { '--': separatedArgs ? separatedArgs : [], engine, platform, project }; } determineEngineFromCommandLine(options) { if (options['engine']) { return String(options['engine']); } if (options['cordova']) { return 'cordova'; } return 'browser'; } beforeBuild(options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { const hook = new BuildBeforeHook(this.e); try { yield hook.run({ name: hook.name, build: options }); } catch (e) { if (e instanceof cli_framework_1.BaseError) { throw new errors_1.FatalException(e.message); } throw e; } }); } run(options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { if (options.engine === 'cordova' && !options.platform) { this.e.log.warn(`Cordova engine chosen without a target platform. This could cause issues. Please use the ${chalk_1.default.green('--platform')} option.`); } yield this.beforeBuild(options); yield this.buildProject(options); yield this.afterBuild(options); }); } afterBuild(options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { const hook = new BuildAfterHook(this.e); try { yield hook.run({ name: hook.name, build: options }); } catch (e) { if (e instanceof cli_framework_1.BaseError) { throw new errors_1.FatalException(e.message); } throw e; } }); } } exports.BuildRunner = BuildRunner; class BuildCLI { constructor(e) { this.e = e; this.resolvedProgram = this.program; } build(options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { this.resolvedProgram = yield this.resolveProgram(); yield this.runWrapper(options); }); } runWrapper(options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { try { return yield this.run(options); } catch (e) { if (!(e instanceof errors_1.BuildCLIProgramNotFoundException)) { throw e; } this.e.log.nl(); this.e.log.info(`Looks like ${chalk_1.default.green(this.pkg)} isn't installed in this project.\n` + `This package is required for this command to work properly.`); const installed = yield this.promptToInstall(); if (!installed) { this.e.log.nl(); throw new errors_1.FatalException(`${chalk_1.default.green(this.pkg)} is required for this command to work properly.`); } return this.run(options); } }); } run(options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { const args = yield this.buildArgs(options); try { yield this.e.shell.run(this.resolvedProgram, args, { cwd: this.e.project.directory, fatalOnNotFound: false }); } catch (e) { if (e instanceof cli_framework_1.ShellCommandError && e.code === cli_framework_1.ERROR_SHELL_COMMAND_NOT_FOUND) { throw new errors_1.BuildCLIProgramNotFoundException(`${chalk_1.default.bold(this.resolvedProgram)} command not found.`); } throw e; } }); } resolveProgram() { return tslib_1.__awaiter(this, void 0, void 0, function* () { if (typeof this.script !== 'undefined') { debug(`Looking for ${chalk_1.default.cyan(this.script)} npm script.`); const pkg = yield this.e.project.requirePackageJson(); if (pkg.scripts && pkg.scripts[this.script]) { debug(`Using ${chalk_1.default.cyan(this.script)} npm script.`); return this.e.config.get('npmClient'); } } return this.program; }); } promptToInstall() { return tslib_1.__awaiter(this, void 0, void 0, function* () { const { pkgManagerArgs } = yield Promise.resolve().then(() => require('./utils/npm')); const [manager, ...managerArgs] = yield pkgManagerArgs(this.e.config.get('npmClient'), { command: 'install', pkg: this.pkg, saveDev: true, saveExact: true }); this.e.log.nl(); const confirm = yield this.e.prompt({ name: 'confirm', message: `Install ${chalk_1.default.green(this.pkg)}?`, type: 'confirm', }); if (!confirm) { this.e.log.warn(`Not installing--here's how to install manually: ${chalk_1.default.green(`${manager} ${managerArgs.join(' ')}`)}`); return false; } yield this.e.shell.run(manager, managerArgs, { cwd: this.e.project.directory }); return true; }); } } exports.BuildCLI = BuildCLI; class BuildBeforeHook extends hooks_1.Hook { constructor() { super(...arguments); this.name = 'build:before'; } } class BuildAfterHook extends hooks_1.Hook { constructor() { super(...arguments); this.name = 'build:after'; } } function build(deps, inputs, options) { return tslib_1.__awaiter(this, void 0, void 0, function* () { try { const runner = yield deps.project.requireBuildRunner(); if (deps.project.name) { options['project'] = deps.project.name; } const opts = runner.createOptionsFromCommandLine(inputs, options); yield runner.run(opts); } catch (e) { if (e instanceof errors_1.RunnerException) { throw new errors_1.FatalException(e.message); } throw e; } }); } exports.build = build;