From 3df1289cd9861d2e7fe4c2ed4253ac43071a91cf Mon Sep 17 00:00:00 2001 From: Evan You Date: Fri, 2 Feb 2018 15:25:10 -0500 Subject: [PATCH] feat: check and show newer version on create --- packages/@vue/cli/lib/Creator.js | 16 ++++------- packages/@vue/cli/lib/options.js | 3 +- packages/@vue/cli/lib/util/clearConsole.js | 30 ++++++++++++++------ packages/@vue/cli/lib/util/getVersions.js | 29 +++++++++++++++++++ packages/vue-cli-version-marker/README.md | 5 ++++ packages/vue-cli-version-marker/package.json | 7 +++++ 6 files changed, 69 insertions(+), 21 deletions(-) create mode 100644 packages/@vue/cli/lib/util/getVersions.js create mode 100644 packages/vue-cli-version-marker/README.md create mode 100644 packages/vue-cli-version-marker/package.json diff --git a/packages/@vue/cli/lib/Creator.js b/packages/@vue/cli/lib/Creator.js index e8e86927d4..23c43d0a5f 100644 --- a/packages/@vue/cli/lib/Creator.js +++ b/packages/@vue/cli/lib/Creator.js @@ -1,12 +1,12 @@ const chalk = require('chalk') const debug = require('debug') const execa = require('execa') -const axios = require('axios') const resolve = require('resolve') const inquirer = require('inquirer') const Generator = require('./Generator') const cloneDeep = require('lodash.clonedeep') const sortObject = require('./util/sortObject') +const getVersions = require('./util/getVersions') const installDeps = require('./util/installDeps') const clearConsole = require('./util/clearConsole') const PromptModuleAPI = require('./PromptModuleAPI') @@ -89,17 +89,11 @@ module.exports = class Creator { (hasYarn ? 'yarn' : 'npm') ) - clearConsole() + await clearConsole() logWithSpinner(`✨`, `Creating project in ${chalk.yellow(context)}.`) // get latest CLI version - let latestCLIVersion - if (!isTestOrDebug) { - const res = await axios.get(`https://registry.npmjs.org/@vue%2Fcli/`) - latestCLIVersion = res.data['dist-tags'].latest - } else { - latestCLIVersion = require('../package.json').version - } + const { latest } = await getVersions() // generate package.json with plugin dependencies const pkg = { name, @@ -109,7 +103,7 @@ module.exports = class Creator { } const deps = Object.keys(preset.plugins) deps.forEach(dep => { - pkg.devDependencies[dep] = `^${latestCLIVersion}` + pkg.devDependencies[dep] = `^${latest}` }) // write package.json await writeFileTree(context, { @@ -185,7 +179,7 @@ module.exports = class Creator { async promptAndResolvePreset () { // prompt - clearConsole() + await clearConsole() const answers = await inquirer.prompt(this.resolveFinalPrompts()) debug('vue-cli:answers')(answers) diff --git a/packages/@vue/cli/lib/options.js b/packages/@vue/cli/lib/options.js index f3c6c28977..5975952742 100644 --- a/packages/@vue/cli/lib/options.js +++ b/packages/@vue/cli/lib/options.js @@ -2,7 +2,8 @@ const fs = require('fs') const os = require('os') const path = require('path') const cloneDeep = require('lodash.clonedeep') -const { error, log, createSchema, validate } = require('@vue/cli-shared-utils') +const { error, log } = require('@vue/cli-shared-utils/lib/logger') +const { createSchema, validate } = require('@vue/cli-shared-utils/lib/validate') const rcPath = exports.rcPath = ( process.env.VUE_CLI_CONFIG_PATH || diff --git a/packages/@vue/cli/lib/util/clearConsole.js b/packages/@vue/cli/lib/util/clearConsole.js index 44f41fae64..bed0b7891b 100644 --- a/packages/@vue/cli/lib/util/clearConsole.js +++ b/packages/@vue/cli/lib/util/clearConsole.js @@ -1,13 +1,25 @@ const chalk = require('chalk') -const version = require('../../package.json').version +const semver = require('semver') +const getVersions = require('./getVersions') const { clearConsole } = require('@vue/cli-shared-utils') -let title = chalk.bold.green(`Vue CLI v${version}`) -if (process.env.VUE_CLI_TEST) { - title += ' ' + chalk.blue.bold('TEST') -} -if (process.env.VUE_CLI_DEBUG) { - title += ' ' + chalk.magenta.bold('DEBUG') -} +module.exports = async function clearConsoleWithTitle () { + const { current, latest } = await getVersions() + + let title = chalk.bold.blue(`Vue CLI v${current}`) -module.exports = () => clearConsole(title) + if (process.env.VUE_CLI_TEST) { + title += ' ' + chalk.blue.bold('TEST') + } + if (process.env.VUE_CLI_DEBUG) { + title += ' ' + chalk.magenta.bold('DEBUG') + } + if (semver.gt(latest, current)) { + title += chalk.green(` +┌─────────────────────────${`─`.repeat(latest.length)}─┐ +│ ✨ Update available: ${latest} ✨ │ +└─────────────────────────${`─`.repeat(latest.length)}─┘`) + } + + clearConsole(title) +} diff --git a/packages/@vue/cli/lib/util/getVersions.js b/packages/@vue/cli/lib/util/getVersions.js new file mode 100644 index 0000000000..b33201f5c4 --- /dev/null +++ b/packages/@vue/cli/lib/util/getVersions.js @@ -0,0 +1,29 @@ +module.exports = async function getVersions () { + const current = require(`../../package.json`).version + let latest + if (process.env.VUE_CLI_LATEST_VERSION) { + // cached value + latest = process.env.VUE_CLI_LATEST_VERSION + } else if (process.env.VUE_CLI_TEST || process.env.VUE_CLI_DEBUG) { + // test/debug, use local version + latest = process.env.VUE_CLI_LATEST_VERSION = current + } else { + const axios = require('axios') + const options = require('../options').loadOptions() + const registry = options.useTaobaoRegistry + ? `https://registry.npm.taobao.org` + : `https://registry.npmjs.org` + + const res = await axios.get(`${registry}/vue-cli-version-marker/latest`) + if (res.status === 200) { + latest = process.env.VUE_CLI_LATEST_VERSION = res.data.version + } else { + // fallback to local version + latest = process.env.VUE_CLI_LATEST_VERSION = current + } + } + return { + current, + latest + } +} diff --git a/packages/vue-cli-version-marker/README.md b/packages/vue-cli-version-marker/README.md new file mode 100644 index 0000000000..0cd2839654 --- /dev/null +++ b/packages/vue-cli-version-marker/README.md @@ -0,0 +1,5 @@ +# What is This? + +The npm registry does not expose `/latest` endpoints for scoped packages. Getting the full metadata for a scoped package is typically `~300ms` slower than simply getting the latest version from an unscoped package. + +This package serves as an unscoped marker to expose the latest version currently published for `@vue/cli`. diff --git a/packages/vue-cli-version-marker/package.json b/packages/vue-cli-version-marker/package.json new file mode 100644 index 0000000000..1b13874441 --- /dev/null +++ b/packages/vue-cli-version-marker/package.json @@ -0,0 +1,7 @@ +{ + "name": "vue-cli-version-marker", + "version": "3.0.0-alpha.6", + "description": "version marker for @vue/cli", + "author": "Evan You", + "license": "MIT" +}