create-vue 3.0.0-beta.3 → 3.0.0-beta.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (25) hide show
  1. package/outfile.cjs +163 -144
  2. package/package.json +6 -7
  3. package/template/base/package.json +4 -6
  4. package/template/base/vite.config.js +3 -1
  5. package/template/code/default/src/App.vue +2 -2
  6. package/template/code/default/src/components/{Welcome.vue → TheWelcome.vue} +0 -0
  7. package/template/code/router/src/App.vue +8 -8
  8. package/template/code/router/src/components/{Welcome.vue → TheWelcome.vue} +0 -0
  9. package/template/code/router/src/router/index.js +16 -18
  10. package/template/code/router/src/views/{About.vue → AboutView.vue} +0 -0
  11. package/template/code/router/src/views/{Home.vue → HomeView.vue} +2 -2
  12. package/template/code/typescript-default/src/App.vue +2 -2
  13. package/template/code/typescript-default/src/components/{Welcome.vue → TheWelcome.vue} +0 -0
  14. package/template/code/typescript-router/src/App.vue +8 -8
  15. package/template/code/typescript-router/src/components/{Welcome.vue → TheWelcome.vue} +0 -0
  16. package/template/code/typescript-router/src/router/index.ts +16 -20
  17. package/template/code/typescript-router/src/views/{About.vue → AboutView.vue} +0 -0
  18. package/template/code/typescript-router/src/views/{Home.vue → HomeView.vue} +2 -2
  19. package/template/config/cypress/package.json +5 -5
  20. package/template/config/jsx/package.json +1 -1
  21. package/template/config/jsx/vite.config.js +3 -1
  22. package/template/config/router/package.json +1 -1
  23. package/template/config/typescript/package.json +2 -2
  24. package/template/config/typescript/tsconfig.json +1 -0
  25. package/index.js +0 -316
package/index.js DELETED
@@ -1,316 +0,0 @@
1
- #!/usr/bin/env node
2
- // @ts-check
3
-
4
- import fs from 'fs'
5
- import path from 'path'
6
-
7
- import minimist from 'minimist'
8
- import prompts from 'prompts'
9
- import { red, green, bold } from 'kolorist'
10
-
11
- import renderTemplate from './utils/renderTemplate.js'
12
- import { postOrderDirectoryTraverse, preOrderDirectoryTraverse } from './utils/directoryTraverse.js'
13
- import generateReadme from './utils/generateReadme.js'
14
- import getCommand from './utils/getCommand.js'
15
-
16
- function isValidPackageName(projectName) {
17
- return /^(?:@[a-z0-9-*~][a-z0-9-*._~]*\/)?[a-z0-9-~][a-z0-9-._~]*$/.test(projectName)
18
- }
19
-
20
- function toValidPackageName(projectName) {
21
- return projectName
22
- .trim()
23
- .toLowerCase()
24
- .replace(/\s+/g, '-')
25
- .replace(/^[._]/, '')
26
- .replace(/[^a-z0-9-~]+/g, '-')
27
- }
28
-
29
- function canSafelyOverwrite(dir) {
30
- return !fs.existsSync(dir) || fs.readdirSync(dir).length === 0
31
- }
32
-
33
- function emptyDir(dir) {
34
- postOrderDirectoryTraverse(
35
- dir,
36
- (dir) => fs.rmdirSync(dir),
37
- (file) => fs.unlinkSync(file)
38
- )
39
- }
40
-
41
- async function init() {
42
- const cwd = process.cwd()
43
- // possible options:
44
- // --default
45
- // --typescript / --ts
46
- // --jsx
47
- // --router / --vue-router
48
- // --vuex
49
- // --with-tests / --tests / --cypress
50
- // --force (for force overwriting)
51
- const argv = minimist(process.argv.slice(2), {
52
- alias: {
53
- typescript: ['ts'],
54
- 'with-tests': ['tests', 'cypress'],
55
- router: ['vue-router']
56
- },
57
- // all arguments are treated as booleans
58
- boolean: true
59
- })
60
-
61
- // if any of the feature flags is set, we would skip the feature prompts
62
- // use `??` instead of `||` once we drop Node.js 12 support
63
- const isFeatureFlagsUsed =
64
- typeof (argv.default || argv.ts || argv.jsx || argv.router || argv.vuex || argv.tests) ===
65
- 'boolean'
66
-
67
- let targetDir = argv._[0]
68
- const defaultProjectName = !targetDir ? 'vue-project' : targetDir
69
-
70
- const forceOverwrite = argv.force
71
-
72
- let result = {}
73
-
74
- try {
75
- // Prompts:
76
- // - Project name:
77
- // - whether to overwrite the existing directory or not?
78
- // - enter a valid package name for package.json
79
- // - Project language: JavaScript / TypeScript
80
- // - Add JSX Support?
81
- // - Install Vue Router for SPA development?
82
- // - Install Vuex for state management? (TODO)
83
- // - Add Cypress for testing?
84
- result = await prompts(
85
- [
86
- {
87
- name: 'projectName',
88
- type: targetDir ? null : 'text',
89
- message: 'Project name:',
90
- initial: defaultProjectName,
91
- onState: (state) => (targetDir = String(state.value).trim() || defaultProjectName)
92
- },
93
- {
94
- name: 'shouldOverwrite',
95
- type: () => (canSafelyOverwrite(targetDir) || forceOverwrite ? null : 'confirm'),
96
- message: () => {
97
- const dirForPrompt =
98
- targetDir === '.' ? 'Current directory' : `Target directory "${targetDir}"`
99
-
100
- return `${dirForPrompt} is not empty. Remove existing files and continue?`
101
- }
102
- },
103
- {
104
- name: 'overwriteChecker',
105
- type: (prev, values = {}) => {
106
- if (values.shouldOverwrite === false) {
107
- throw new Error(red('✖') + ' Operation cancelled')
108
- }
109
- return null
110
- }
111
- },
112
- {
113
- name: 'packageName',
114
- type: () => (isValidPackageName(targetDir) ? null : 'text'),
115
- message: 'Package name:',
116
- initial: () => toValidPackageName(targetDir),
117
- validate: (dir) => isValidPackageName(dir) || 'Invalid package.json name'
118
- },
119
- {
120
- name: 'needsTypeScript',
121
- type: () => (isFeatureFlagsUsed ? null : 'toggle'),
122
- message: 'Add TypeScript?',
123
- initial: false,
124
- active: 'Yes',
125
- inactive: 'No'
126
- },
127
- {
128
- name: 'needsJsx',
129
- type: () => (isFeatureFlagsUsed ? null : 'toggle'),
130
- message: 'Add JSX Support?',
131
- initial: false,
132
- active: 'Yes',
133
- inactive: 'No'
134
- },
135
- {
136
- name: 'needsRouter',
137
- type: () => (isFeatureFlagsUsed ? null : 'toggle'),
138
- message: 'Add Vue Router for Single Page Application development?',
139
- initial: false,
140
- active: 'Yes',
141
- inactive: 'No'
142
- },
143
- {
144
- name: 'needsVuex',
145
- type: () => (isFeatureFlagsUsed ? null : 'toggle'),
146
- message: 'Add Vuex for state management?',
147
- initial: false,
148
- active: 'Yes',
149
- inactive: 'No'
150
- },
151
- {
152
- name: 'needsTests',
153
- type: () => (isFeatureFlagsUsed ? null : 'toggle'),
154
- message: 'Add Cypress for testing?',
155
- initial: false,
156
- active: 'Yes',
157
- inactive: 'No'
158
- }
159
- ],
160
- {
161
- onCancel: () => {
162
- throw new Error(red('✖') + ' Operation cancelled')
163
- }
164
- }
165
- )
166
- } catch (cancelled) {
167
- console.log(cancelled.message)
168
- process.exit(1)
169
- }
170
-
171
- // `initial` won't take effect if the prompt type is null
172
- // so we still have to assign the default values here
173
- const {
174
- packageName = toValidPackageName(defaultProjectName),
175
- shouldOverwrite,
176
- needsJsx = argv.jsx,
177
- needsTypeScript = argv.typescript,
178
- needsRouter = argv.router,
179
- needsVuex = argv.vuex,
180
- needsTests = argv.tests
181
- } = result
182
- const root = path.join(cwd, targetDir)
183
-
184
- if (shouldOverwrite) {
185
- emptyDir(root)
186
- } else if (!fs.existsSync(root)) {
187
- fs.mkdirSync(root)
188
- }
189
-
190
- console.log(`\nScaffolding project in ${root}...`)
191
-
192
- const pkg = { name: packageName, version: '0.0.0' }
193
- fs.writeFileSync(path.resolve(root, 'package.json'), JSON.stringify(pkg, null, 2))
194
-
195
- // todo:
196
- // work around the esbuild issue that `import.meta.url` cannot be correctly transpiled
197
- // when bundling for node and the format is cjs
198
- // const templateRoot = new URL('./template', import.meta.url).pathname
199
- const templateRoot = path.resolve(__dirname, 'template')
200
- const render = function render(templateName) {
201
- const templateDir = path.resolve(templateRoot, templateName)
202
- renderTemplate(templateDir, root)
203
- }
204
-
205
- // Render base template
206
- render('base')
207
-
208
- // Add configs.
209
- if (needsJsx) {
210
- render('config/jsx')
211
- }
212
- if (needsRouter) {
213
- render('config/router')
214
- }
215
- if (needsVuex) {
216
- render('config/vuex')
217
- }
218
- if (needsTests) {
219
- render('config/cypress')
220
- }
221
- if (needsTypeScript) {
222
- render('config/typescript')
223
- }
224
-
225
- // Render code template.
226
- // prettier-ignore
227
- const codeTemplate =
228
- (needsTypeScript ? 'typescript-' : '') +
229
- (needsRouter ? 'router' : 'default')
230
- render(`code/${codeTemplate}`)
231
-
232
- // Render entry file (main.js/ts).
233
- if (needsVuex && needsRouter) {
234
- render('entry/vuex-and-router')
235
- } else if (needsVuex) {
236
- render('entry/vuex')
237
- } else if (needsRouter) {
238
- render('entry/router')
239
- } else {
240
- render('entry/default')
241
- }
242
-
243
- // Cleanup.
244
-
245
- if (needsTypeScript) {
246
- // rename all `.js` files to `.ts`
247
- // rename jsconfig.json to tsconfig.json
248
- preOrderDirectoryTraverse(
249
- root,
250
- () => {},
251
- (filepath) => {
252
- if (filepath.endsWith('.js')) {
253
- fs.renameSync(filepath, filepath.replace(/\.js$/, '.ts'))
254
- } else if (path.basename(filepath) === 'jsconfig.json') {
255
- fs.renameSync(filepath, filepath.replace(/jsconfig\.json$/, 'tsconfig.json'))
256
- }
257
- }
258
- )
259
-
260
- // Rename entry in `index.html`
261
- const indexHtmlPath = path.resolve(root, 'index.html')
262
- const indexHtmlContent = fs.readFileSync(indexHtmlPath, 'utf8')
263
- fs.writeFileSync(indexHtmlPath, indexHtmlContent.replace('src/main.js', 'src/main.ts'))
264
- }
265
-
266
- if (!needsTests) {
267
- // All templates assumes the need of tests.
268
- // If the user doesn't need it:
269
- // rm -rf cypress **/__tests__/
270
- preOrderDirectoryTraverse(
271
- root,
272
- (dirpath) => {
273
- const dirname = path.basename(dirpath)
274
-
275
- if (dirname === 'cypress' || dirname === '__tests__') {
276
- emptyDir(dirpath)
277
- fs.rmdirSync(dirpath)
278
- }
279
- },
280
- () => {}
281
- )
282
- }
283
-
284
- // Instructions:
285
- // Supported package managers: pnpm > yarn > npm
286
- // Note: until <https://github.com/pnpm/pnpm/issues/3505> is resolved,
287
- // it is not possible to tell if the command is called by `pnpm init`.
288
- const packageManager = /pnpm/.test(process.env.npm_execpath)
289
- ? 'pnpm'
290
- : /yarn/.test(process.env.npm_execpath)
291
- ? 'yarn'
292
- : 'npm'
293
-
294
- // README generation
295
- fs.writeFileSync(
296
- path.resolve(root, 'README.md'),
297
- generateReadme({
298
- projectName: result.projectName || defaultProjectName,
299
- packageManager,
300
- needsTypeScript,
301
- needsTests
302
- })
303
- )
304
-
305
- console.log(`\nDone. Now run:\n`)
306
- if (root !== cwd) {
307
- console.log(` ${bold(green(`cd ${path.relative(cwd, root)}`))}`)
308
- }
309
- console.log(` ${bold(green(getCommand(packageManager, 'install')))}`)
310
- console.log(` ${bold(green(getCommand(packageManager, 'dev')))}`)
311
- console.log()
312
- }
313
-
314
- init().catch((e) => {
315
- console.error(e)
316
- })