UNPKG

isun

Version:

快速创建vue项目

293 lines (254 loc) 10.6 kB
#!/usr/bin/env node // Check node version before requiring/doing anything else // The user may be on a very old node version const { chalk, semver } = require('@vue/cli-shared-utils') const requiredVersion = require('../package.json').engines.node const leven = require('leven') function checkNodeVersion (wanted, id) { if (!semver.satisfies(process.version, wanted)) { console.log(chalk.red( 'You are using Node ' + process.version + ', but this version of ' + id + ' requires Node ' + wanted + '.\nPlease upgrade your Node version.' )) process.exit(1) } } checkNodeVersion(requiredVersion, '@vue/cli') if (semver.satisfies(process.version, '9.x')) { console.log(chalk.red( `You are using Node ${process.version}.\n` + `Node.js 9.x has already reached end-of-life and will not be supported in future major releases.\n` + `It's strongly recommended to use an active LTS version instead.` )) } const fs = require('fs') const path = require('path') const slash = require('slash') const minimist = require('minimist') // enter debug mode when creating test repo if ( slash(process.cwd()).indexOf('/packages/test') > 0 && ( fs.existsSync(path.resolve(process.cwd(), '../@vue')) || fs.existsSync(path.resolve(process.cwd(), '../../@vue')) ) ) { process.env.VUE_CLI_DEBUG = true } const program = require('commander') const loadCommand = require('../lib/util/loadCommand') program .version(`@vue/cli ${require('../package').version}`) .usage('<command> [options]') program .command('create <app-name>') .description('create a new project powered by vue-cli-service') .option('-p, --preset <presetName>', 'Skip prompts and use saved or remote preset') .option('-d, --default', 'Skip prompts and use default preset') .option('-i, --inlinePreset <json>', 'Skip prompts and use inline JSON string as preset') .option('-m, --packageManager <command>', 'Use specified npm client when installing dependencies') .option('-r, --registry <url>', 'Use specified npm registry when installing dependencies (only for npm)') .option('-g, --git [message]', 'Force git initialization with initial commit message') .option('-n, --no-git', 'Skip git initialization') .option('-f, --force', 'Overwrite target directory if it exists') .option('--merge', 'Merge target directory if it exists') .option('-c, --clone', 'Use git clone when fetching remote preset') .option('-x, --proxy', 'Use specified proxy when creating project') .option('-b, --bare', 'Scaffold project without beginner instructions') .option('--skipGetStarted', 'Skip displaying "Get started" instructions') .action((name, cmd) => { const options = cleanArgs(cmd) if (minimist(process.argv.slice(3))._.length > 1) { console.log(chalk.yellow('\n Info: You provided more than one argument. The first one will be used as the app\'s name, the rest are ignored.')) } // --git makes commander to default git to true if (process.argv.includes('-g') || process.argv.includes('--git')) { options.forceGit = true } require('../lib/create')(name, options) }) program .command('add <plugin> [pluginOptions]') .description('install a plugin and invoke its generator in an already created project') .option('--registry <url>', 'Use specified npm registry when installing dependencies (only for npm)') .allowUnknownOption() .action((plugin) => { require('../lib/add')(plugin, minimist(process.argv.slice(3))) }) program .command('invoke <plugin> [pluginOptions]') .description('invoke the generator of a plugin in an already created project') .option('--registry <url>', 'Use specified npm registry when installing dependencies (only for npm)') .allowUnknownOption() .action((plugin) => { require('../lib/invoke')(plugin, minimist(process.argv.slice(3))) }) program .command('inspect [paths...]') .description('inspect the webpack config in a project with vue-cli-service') .option('--mode <mode>') .option('--rule <ruleName>', 'inspect a specific module rule') .option('--plugin <pluginName>', 'inspect a specific plugin') .option('--rules', 'list all module rule names') .option('--plugins', 'list all plugin names') .option('-v --verbose', 'Show full function definitions in output') .action((paths, cmd) => { require('../lib/inspect')(paths, cleanArgs(cmd)) }) program .command('serve [entry]') .description('serve a .js or .vue file in development mode with zero config') .option('-o, --open', 'Open browser') .option('-c, --copy', 'Copy local url to clipboard') .option('-p, --port <port>', 'Port used by the server (default: 8080 or next available port)') .action((entry, cmd) => { loadCommand('serve', '@vue/cli-service-global').serve(entry, cleanArgs(cmd)) }) program .command('build [entry]') .description('build a .js or .vue file in production mode with zero config') .option('-t, --target <target>', 'Build target (app | lib | wc | wc-async, default: app)') .option('-n, --name <name>', 'name for lib or web-component mode (default: entry filename)') .option('-d, --dest <dir>', 'output directory (default: dist)') .action((entry, cmd) => { loadCommand('build', '@vue/cli-service-global').build(entry, cleanArgs(cmd)) }) program .command('ui') .description('start and open the vue-cli ui') .option('-H, --host <host>', 'Host used for the UI server (default: localhost)') .option('-p, --port <port>', 'Port used for the UI server (by default search for available port)') .option('-D, --dev', 'Run in dev mode') .option('--quiet', `Don't output starting messages`) .option('--headless', `Don't open browser on start and output port`) .action((cmd) => { checkNodeVersion('>=8.6', 'vue ui') require('../lib/ui')(cleanArgs(cmd)) }) program .command('init <template> <app-name>') .description('generate a project from a remote template (legacy API, requires @vue/cli-init)') .option('-c, --clone', 'Use git clone when fetching remote template') .option('--offline', 'Use cached template') .action(() => { loadCommand('init', '@vue/cli-init') }) program .command('config [value]') .description('inspect and modify the config') .option('-g, --get <path>', 'get value from option') .option('-s, --set <path> <value>', 'set option value') .option('-d, --delete <path>', 'delete option from config') .option('-e, --edit', 'open config with default editor') .option('--json', 'outputs JSON result only') .action((value, cmd) => { require('../lib/config')(value, cleanArgs(cmd)) }) program .command('outdated') .description('(experimental) check for outdated vue cli service / plugins') .option('--next', 'Also check for alpha / beta / rc versions when upgrading') .action((cmd) => { require('../lib/outdated')(cleanArgs(cmd)) }) program .command('upgrade [plugin-name]') .description('(experimental) upgrade vue cli service / plugins') .option('-t, --to <version>', 'Upgrade <package-name> to a version that is not latest') .option('-f, --from <version>', 'Skip probing installed plugin, assuming it is upgraded from the designated version') .option('-r, --registry <url>', 'Use specified npm registry when installing dependencies') .option('--all', 'Upgrade all plugins') .option('--next', 'Also check for alpha / beta / rc versions when upgrading') .action((packageName, cmd) => { require('../lib/upgrade')(packageName, cleanArgs(cmd)) }) program .command('migrate [plugin-name]') .description('(experimental) run migrator for an already-installed cli plugin') // TODO: use `requiredOption` after upgrading to commander 4.x .option('-f, --from <version>', 'The base version for the migrator to migrate from') .action((packageName, cmd) => { require('../lib/migrate')(packageName, cleanArgs(cmd)) }) program .command('info') .description('print debugging information about your environment') .action((cmd) => { console.log(chalk.bold('\nEnvironment Info:')) require('envinfo').run( { System: ['OS', 'CPU'], Binaries: ['Node', 'Yarn', 'npm'], Browsers: ['Chrome', 'Edge', 'Firefox', 'Safari'], npmPackages: '/**/{typescript,*vue*,@vue/*/}', npmGlobalPackages: ['@vue/cli'] }, { showNotFound: true, duplicates: true, fullTree: true } ).then(console.log) }) // output help information on unknown commands program .arguments('<command>') .action((cmd) => { program.outputHelp() console.log(` ` + chalk.red(`Unknown command ${chalk.yellow(cmd)}.`)) console.log() suggestCommands(cmd) }) // add some useful info on help program.on('--help', () => { console.log() console.log(` Run ${chalk.cyan(`vue <command> --help`)} for detailed usage of given command.`) console.log() }) program.commands.forEach(c => c.on('--help', () => console.log())) // enhance common error messages const enhanceErrorMessages = require('../lib/util/enhanceErrorMessages') enhanceErrorMessages('missingArgument', argName => { return `Missing required argument ${chalk.yellow(`<${argName}>`)}.` }) enhanceErrorMessages('unknownOption', optionName => { return `Unknown option ${chalk.yellow(optionName)}.` }) enhanceErrorMessages('optionMissingArgument', (option, flag) => { return `Missing required argument for option ${chalk.yellow(option.flags)}` + ( flag ? `, got ${chalk.yellow(flag)}` : `` ) }) program.parse(process.argv) if (!process.argv.slice(2).length) { program.outputHelp() } function suggestCommands (unknownCommand) { const availableCommands = program.commands.map(cmd => cmd._name) let suggestion availableCommands.forEach(cmd => { const isBestMatch = leven(cmd, unknownCommand) < leven(suggestion || '', unknownCommand) if (leven(cmd, unknownCommand) < 3 && isBestMatch) { suggestion = cmd } }) if (suggestion) { console.log(` ` + chalk.red(`Did you mean ${chalk.yellow(suggestion)}?`)) } } function camelize (str) { return str.replace(/-(\w)/g, (_, c) => c ? c.toUpperCase() : '') } // commander passes the Command object itself as options, // extract only actual options into a fresh object. function cleanArgs (cmd) { const args = {} cmd.options.forEach(o => { const key = camelize(o.long.replace(/^--/, '')) // if an option is not present and Command has a method with the same name // it should not be copied if (typeof cmd[key] !== 'function' && typeof cmd[key] !== 'undefined') { args[key] = cmd[key] } }) return args }