UNPKG

@wpk-cli/cli

Version:

an unofficial CLI for webpack

331 lines (249 loc) 9.17 kB
"use strict"; var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault"); Object.defineProperty(exports, "__esModule", { value: true }); exports.getCommandDefaults = getCommandDefaults; exports.applyUserConfigOptions = applyUserConfigOptions; exports.printCommandError = printCommandError; exports.processError = processError; exports.cleanConsole = cleanConsole; exports.logCommandInfo = logCommandInfo; exports.logWebpackInfo = logWebpackInfo; exports.logEnvInfo = logEnvInfo; exports.checkForUpdateMaybe = checkForUpdateMaybe; exports.prepareCmd = prepareCmd; exports.enhanceCommander = enhanceCommander; var _semver = _interopRequireDefault(require("semver")); var _execa = _interopRequireDefault(require("execa")); var _set = _interopRequireDefault(require("lodash/set")); var _includes = _interopRequireDefault(require("lodash/includes")); var _reduce = _interopRequireDefault(require("lodash/reduce")); var _split = _interopRequireDefault(require("lodash/split")); var _get = _interopRequireDefault(require("lodash/get")); var _chalk = _interopRequireDefault(require("chalk")); var _logger = _interopRequireDefault(require("@wpk-cli/logger")); var _ansiEscapes = _interopRequireDefault(require("ansi-escapes")); var _getCursorPosition = _interopRequireDefault(require("get-cursor-position")); var _keys = _interopRequireDefault(require("lodash/keys")); var _toLower = _interopRequireDefault(require("lodash/toLower")); var _startsWith = _interopRequireDefault(require("lodash/startsWith")); var _user = _interopRequireDefault(require("@wpk-cli/user")); var _utilities = require("@wpk-cli/utilities"); var _package = _interopRequireDefault(require("../package.json")); var _commands = require("./commands"); const defaultsIgnore = ["WPK_PROFILE"]; let commandDefaults; /** Gather command default from the environment. */ function getCommandDefaults() { if (commandDefaults) { return commandDefaults; } const value = (0, _reduce.default)((0, _keys.default)(process.env), (defaults, key) => { if ((0, _includes.default)(defaultsIgnore, key)) { return defaults; } if ((0, _startsWith.default)(key, "WPK_")) { const lowerKey = (0, _toLower.default)(key.replace(/^WPK_/, "")); defaults[lowerKey] = process.env[key]; } return defaults; }, {}); commandDefaults = value; return value; } /** Apply user config options to the environment. */ function applyUserConfigOptions() { const globals = { color: value => { process.env.FORCE_COLOR = value; } }; for (const opt in globals) { const value = _user.default.get("global." + opt); if (value) { globals[opt](value); } } } /** * Like `printError` in @wpk-cli/utilities but for command installation and execution errors * that have extra messages. * @param err {Error} the error * @param command {Object} wpk command definition object * @param what {String} operation name that errored */ function printCommandError(err, command, what) { _logger.default.intercept.restore(); const name = (0, _get.default)(command, "name") || (0, _get.default)(command, "_location") || command; const native = name in _commands.nativeCommandNames; const messages = [`failed to ${what} command "${name}" ` + ((0, _get.default)(command, "_where") ? `(${(0, _get.default)(command, "_where")})` : "")]; if (!native && (0, _get.default)(command, "_location")) { messages.push("remove this package and file an issue with the author"); let pkg; try { pkg = require(command._location + "/package.json"); } catch (err) {} if (pkg && (pkg.bugs || pkg.homepage)) { messages[1] = messages[1] + ":"; messages.push(pkg.bugs || pkg.homepage); } } (0, _utilities.printError)(err, messages, native); process.exit(1); } /** * Handler for uncaught exceptions. * @param err {Error} the error */ function processError(err) { _logger.default.intercept.restore(); cleanConsole(); (0, _utilities.printError)(err, ["an unknown error occurred"], true); process.exit(1); } /** Clear whatever is beneath the console cursor. */ function cleanConsole() { const cursor = _getCursorPosition.default.sync(); if (cursor) { process.stdout.write(_ansiEscapes.default.cursorSavePosition); for (let i = 0; i < process.stdout.rows - cursor.row; i++) { process.stdout.write(_ansiEscapes.default.cursorDown()); process.stdout.write(_ansiEscapes.default.eraseLine); } process.stdout.write(_ansiEscapes.default.cursorRestorePosition); } } /** * Log information about the command being run, e.g. name, version. * @param command {String} command name * @param thirdParty {Boolean} is the command an add-on? * @returns {String} the command info that was logged */ function logCommandInfo(command, thirdParty = false) { // TODO remove "beta" tag when out of beta let cmdInfo = _chalk.default`wpk ${command} {grey v${_package.default.version} beta}`; if (thirdParty) { cmdInfo += _chalk.default.grey(" (add-on)"); } // TODO make this not set on the global object global.wpk.commandInfo = cmdInfo; if (!global.wpk.noInfoLogs) { (0, _logger.default)(cmdInfo); } return cmdInfo; } /** * Log information about the version and scope of webpack in use. * @param webpack {Object} the webpack package in use * @param scope {"local"|"global"} the scope of the webpack package */ function logWebpackInfo(webpack, scope) { let warn; if (webpack) { // webpack 4 has webpack.version let version = webpack.version; if (!version) { if (webpack && !webpack.version) { // webpack <= 3 does not have version property on main export version = (0, _utilities.getWebpackVersion)(scope); } } // TODO make this not set on the global object global.wpk.webpackInfo = _chalk.default`webpack v${version} {grey (${webpack.scope})}`; if (!global.wpk.noInfoLogs) { _logger.default.info(global.wpk.webpackInfo); } if ((0, _split.default)(version, ".")[0] < 4) { warn = `webpack version unsupported`; } } else { warn = "webpack not found"; } if (!global.wpk.noInfoLogs && warn) { _logger.default.warn(_chalk.default`${warn} {grey (some commands may fail)}`); if (warn === "webpack not found") { _logger.default.warn("install webpack: {grey npm i -g webpack}"); } } } /** Log what defaults are set by the environment. */ function logEnvInfo() { const defaults = getCommandDefaults(); const defaultKeys = (0, _keys.default)(defaults); if (defaultKeys.length) { const len = defaultKeys.length; let i = 0; _logger.default.info("defaults set by environment:", (0, _reduce.default)(defaults, (str, v, k) => { return str + `${k}=${v}` + (i++ === len - 1 ? "" : ", "); }, "")); } } /** * Check if an update to wpk is available. * The check is performed at most once a day. * @param cmd {Object} Commander cmd object */ function checkForUpdateMaybe(cmd) { // TODO reinstate in the future return; if (_user.default.get("global.checkForUpdates")) { const lastCheckedForUpdate = _user.default.get("$.lastCheckedForUpdate"); if (lastCheckedForUpdate) { const oneDayMs = 24 * 60 * 60 * 1000; if (Date.now() - lastCheckedForUpdate < oneDayMs) { return; } } _user.default.set("$.lastCheckedForUpdate", Date.now()); try { const _execa$sync = _execa.default.sync("npm view @wpk-cli/cli version"), stdout = _execa$sync.stdout, stderr = _execa$sync.stderr; if (_semver.default.lt(_package.default.version, stdout)) { // TODO check if @wpk-cli/cli is installed globally by yarn and suggest yarn command instead _logger.default.info(`a newer version of wpk is available: v${stdout}`); _logger.default.info(_chalk.default`run {grey npm i -g @wpk-cli/cli} to update`); } } catch (err) { if (cmd.wpkDebug) { (0, _utilities.printError)(err); global.wpk.exit(1); } } } } /** * Prepare the cmd object to be handed off to a command by removing * the Commander private properties & expanding dot-path properties. * @param cmd {Object} Commander cmd object */ function prepareCmd(cmd) { // remove all Commander.js properties delete cmd.commands; delete cmd.options; delete cmd.parent; for (const key in cmd) { if ((0, _startsWith.default)(key, "_")) { delete cmd[key]; } } // expand dot path flags for (const key in cmd) { /* istanbul ignore next */ if (!cmd.hasOwnProperty(key)) { continue; } if ((0, _includes.default)(key, ".")) { const value = cmd[key]; delete cmd[key]; (0, _set.default)(cmd, key, value); } } } /** Enhance Commander program with extra methods. */ function enhanceCommander(program) { program.Command.prototype.optionMulti = function (option, description) { return this.option(option, description, (val, memo) => { memo.push(val); return memo; }, []); }; }