refactor(project create): run vue create in child process, closes #3664

This commit is contained in:
Guillaume Chau
2019-04-06 01:48:02 +02:00
parent c81e6c21a2
commit 8c3ff11653
5 changed files with 77 additions and 42 deletions
@@ -1,3 +1,14 @@
/** @typedef {'warn' | 'error' | 'info' | 'done'} LogType */
/**
* @typedef Log
* @prop {string} id
* @prop {string} date
* @prop {LogType} type
* @prop {string} tag
* @prop {string} message
*/
const shortId = require('shortid')
const { events } = require('@vue/cli-shared-utils/lib/logger')
const { generateTitle } = require('@vue/cli/lib/util/clearConsole')
@@ -6,9 +17,15 @@ const channels = require('../channels')
// Context
const getContext = require('../context')
/** @type {Log []} */
let logs = []
/**
* @param {Log} log
* @param {any} context
*/
exports.add = function (log, context) {
/** @type {Log} */
const item = {
id: shortId.generate(),
date: new Date().toISOString(),
@@ -5,7 +5,7 @@ const Creator = require('@vue/cli/lib/Creator')
const { getPromptModules } = require('@vue/cli/lib/util/createTools')
const { getFeatures } = require('@vue/cli/lib/util/features')
const { defaults } = require('@vue/cli/lib/options')
const { toShortPluginId, clearModule } = require('@vue/cli-shared-utils')
const { toShortPluginId, execa } = require('@vue/cli-shared-utils')
const { progress: installProgress } = require('@vue/cli/lib/util/installDeps')
const parseGitConfig = require('parse-git-config')
// Connectors
@@ -15,6 +15,7 @@ const prompts = require('./prompts')
const folders = require('./folders')
const plugins = require('./plugins')
const locales = require('./locales')
const logs = require('./logs')
// Context
const getContext = require('../context')
// Utils
@@ -258,53 +259,23 @@ async function create (input, context) {
const targetDir = path.join(cwd.get(), input.folder)
// Delete existing folder
if (fs.existsSync(targetDir)) {
if (input.force) {
setProgress({
info: 'Cleaning folder...'
})
await folders.delete(targetDir)
setProgress({
info: null
})
} else {
throw new Error(`Folder ${targetDir} already exists`)
}
}
cwd.set(targetDir, context)
creator.context = targetDir
process.env.VUE_CLI_CONTEXT = targetDir
clearModule('@vue/cli-service/webpack.config.js', targetDir)
const inCurrent = input.folder === '.'
const name = inCurrent ? path.relative('../', process.cwd()) : input.folder
creator.name = name.toLowerCase()
const name = creator.name = (inCurrent ? path.relative('../', process.cwd()) : input.folder).toLowerCase()
// Answers
const answers = prompts.getAnswers()
await prompts.reset()
let index
// Config files
let index
if ((index = answers.features.indexOf('use-config-files')) !== -1) {
answers.features.splice(index, 1)
answers.useConfigFiles = 'files'
}
const createOptions = {
packageManager: input.packageManager,
bare: input.bare
}
// Git
if (input.enableGit && input.gitCommitMessage) {
createOptions.git = input.gitCommitMessage
} else {
createOptions.git = input.enableGit
}
// Preset
answers.preset = input.preset
if (input.save) {
@@ -330,7 +301,49 @@ async function create (input, context) {
})
// Create
await creator.create(createOptions, preset)
const args = [
'--skipGetStarted'
]
if (input.packageManager) args.push('--packageManager', input.packageManager)
if (input.bar) args.push('--bare')
if (input.force) args.push('--force')
// Git
if (input.enableGit && input.gitCommitMessage) {
args.push('--git', input.gitCommitMessage)
} else if (!input.enableGit) {
args.push('--no-git')
}
// Preset
args.push('--inlinePreset', JSON.stringify(preset))
log('create', name, args)
const child = execa('vue', [
'create',
name,
...args
], {
cwd: cwd.get(),
stdio: ['inherit', 'pipe', 'inherit']
})
const onData = buffer => {
const text = buffer.toString().trim()
if (text) {
setProgress({
info: text
})
logs.add({
type: 'info',
message: text
}, context)
}
}
child.stdout.on('data', onData)
await child
removeCreator()
notify({
@@ -32,9 +32,11 @@
</div>
<div class="secondary-info">
<div v-if="progress.info" class="info">
{{ progress.info }}
</div>
<div
v-if="progress.info"
class="info"
v-html="ansiColors(progress.info)"
/>
<VueLoadingBar
v-if="progress.progress !== -1"
+1
View File
@@ -63,6 +63,7 @@ program
.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)
+7 -5
View File
@@ -210,11 +210,13 @@ module.exports = class Creator extends EventEmitter {
stopSpinner()
log()
log(`🎉 Successfully created project ${chalk.yellow(name)}.`)
log(
`👉 Get started with the following commands:\n\n` +
(this.context === process.cwd() ? `` : chalk.cyan(` ${chalk.gray('$')} cd ${name}\n`)) +
chalk.cyan(` ${chalk.gray('$')} ${packageManager === 'yarn' ? 'yarn serve' : 'npm run serve'}`)
)
if (!cliOptions.skipGetStarted) {
log(
`👉 Get started with the following commands:\n\n` +
(this.context === process.cwd() ? `` : chalk.cyan(` ${chalk.gray('$')} cd ${name}\n`)) +
chalk.cyan(` ${chalk.gray('$')} ${packageManager === 'yarn' ? 'yarn serve' : 'npm run serve'}`)
)
}
log()
this.emit('creation', { event: 'done' })