From 5067d29c990fa9beb77d8251307720c6e82f5971 Mon Sep 17 00:00:00 2001 From: "Mr.Hope" Date: Fri, 29 Dec 2023 14:51:21 +0800 Subject: [PATCH 1/5] feat: add create-helper --- create/package.json | 59 ++++++++ create/src/action.ts | 118 +++++++++++++++ create/src/config/index.ts | 3 + create/src/flow/createPackageJson.ts | 98 +++++++++++++ create/src/flow/generateTemplate.ts | 134 ++++++++++++++++++ create/src/flow/index.ts | 2 + create/src/i18n/en.ts | 45 ++++++ create/src/i18n/index.ts | 32 +++++ create/src/i18n/typings.ts | 40 ++++++ create/src/i18n/zh.ts | 44 ++++++ create/src/index.ts | 25 ++++ create/src/utils/file.ts | 49 +++++++ create/src/utils/getPackageManager.ts | 47 ++++++ create/src/utils/getRegistry.ts | 58 ++++++++ create/src/utils/index.ts | 5 + create/src/utils/normalizeThemeName.ts | 25 ++++ create/src/utils/version.ts | 7 + create/template/blog/.vuepress/blog-plugin.js | 109 ++++++++++++++ create/template/blog/.vuepress/client.js | 15 ++ .../blog/.vuepress/components/ArticleList.vue | 134 ++++++++++++++++++ create/template/blog/.vuepress/config.js | 88 ++++++++++++ .../blog/.vuepress/layouts/Article.vue | 22 +++ .../blog/.vuepress/layouts/Category.vue | 111 +++++++++++++++ .../template/blog/.vuepress/layouts/Tag.vue | 111 +++++++++++++++ .../blog/.vuepress/layouts/Timeline.vue | 30 ++++ create/template/blog/README.md | 33 +++++ create/template/blog/get-started.md | 46 ++++++ create/template/blog/posts/archive1.md | 18 +++ create/template/blog/posts/archive2.md | 18 +++ create/template/blog/posts/article1.md | 18 +++ create/template/blog/posts/article10.md | 19 +++ create/template/blog/posts/article11.md | 19 +++ create/template/blog/posts/article12.md | 19 +++ create/template/blog/posts/article2.md | 18 +++ create/template/blog/posts/article3.md | 19 +++ create/template/blog/posts/article4.md | 19 +++ create/template/blog/posts/article5.md | 19 +++ create/template/blog/posts/article6.md | 19 +++ create/template/blog/posts/article7.md | 19 +++ create/template/blog/posts/article8.md | 19 +++ create/template/blog/posts/article9.md | 19 +++ create/template/blog/posts/sticky.md | 19 +++ create/template/blog/posts/sticky2.md | 22 +++ create/template/docs/.vuepress/config.js | 15 ++ create/template/docs/README.md | 33 +++++ create/template/docs/get-started.md | 46 ++++++ create/tsconfig.build.json | 9 ++ pnpm-lock.yaml | 64 ++++----- pnpm-workspace.yaml | 1 + tsconfig.build.json | 1 + tsconfig.json | 1 + 51 files changed, 1928 insertions(+), 35 deletions(-) create mode 100644 create/package.json create mode 100644 create/src/action.ts create mode 100644 create/src/config/index.ts create mode 100644 create/src/flow/createPackageJson.ts create mode 100644 create/src/flow/generateTemplate.ts create mode 100644 create/src/flow/index.ts create mode 100644 create/src/i18n/en.ts create mode 100644 create/src/i18n/index.ts create mode 100644 create/src/i18n/typings.ts create mode 100644 create/src/i18n/zh.ts create mode 100644 create/src/index.ts create mode 100644 create/src/utils/file.ts create mode 100644 create/src/utils/getPackageManager.ts create mode 100644 create/src/utils/getRegistry.ts create mode 100644 create/src/utils/index.ts create mode 100644 create/src/utils/normalizeThemeName.ts create mode 100644 create/src/utils/version.ts create mode 100644 create/template/blog/.vuepress/blog-plugin.js create mode 100644 create/template/blog/.vuepress/client.js create mode 100644 create/template/blog/.vuepress/components/ArticleList.vue create mode 100644 create/template/blog/.vuepress/config.js create mode 100644 create/template/blog/.vuepress/layouts/Article.vue create mode 100644 create/template/blog/.vuepress/layouts/Category.vue create mode 100644 create/template/blog/.vuepress/layouts/Tag.vue create mode 100644 create/template/blog/.vuepress/layouts/Timeline.vue create mode 100644 create/template/blog/README.md create mode 100644 create/template/blog/get-started.md create mode 100644 create/template/blog/posts/archive1.md create mode 100644 create/template/blog/posts/archive2.md create mode 100644 create/template/blog/posts/article1.md create mode 100644 create/template/blog/posts/article10.md create mode 100644 create/template/blog/posts/article11.md create mode 100644 create/template/blog/posts/article12.md create mode 100644 create/template/blog/posts/article2.md create mode 100644 create/template/blog/posts/article3.md create mode 100644 create/template/blog/posts/article4.md create mode 100644 create/template/blog/posts/article5.md create mode 100644 create/template/blog/posts/article6.md create mode 100644 create/template/blog/posts/article7.md create mode 100644 create/template/blog/posts/article8.md create mode 100644 create/template/blog/posts/article9.md create mode 100644 create/template/blog/posts/sticky.md create mode 100644 create/template/blog/posts/sticky2.md create mode 100644 create/template/docs/.vuepress/config.js create mode 100644 create/template/docs/README.md create mode 100644 create/template/docs/get-started.md create mode 100644 create/tsconfig.build.json diff --git a/create/package.json b/create/package.json new file mode 100644 index 0000000000..eee147b151 --- /dev/null +++ b/create/package.json @@ -0,0 +1,59 @@ +{ + "name": "create-vuepress", + "version": "2.0.0-rc.0", + "description": "VuePress template helper", + "keywords": [ + "vuepress", + "create", + "create-vuepress", + "template" + ], + "homepage": "https://github.com/vuepress", + "bugs": { + "url": "https://github.com/vuepress/ecosystem/issues" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/vuepress/ecosystem.git" + }, + "license": "MIT", + "author": { + "name": "Mr.Hope", + "email": "mister-hope@outlook.com", + "url": "https://mister-hope.com" + }, + "type": "module", + "exports": { + ".": "./lib/index.js", + "./package.json": "./package.json" + }, + "main": "./lib/index.js", + "bin": { + "create-vuepress": "./lib/index.js" + }, + "files": [ + "lib", + "template" + ], + "scripts": { + "build": "tsc -b tsconfig.build.json", + "clean": "rimraf lib *.tsbuildinfo" + }, + "dependencies": { + "cac": "^6.7.14", + "execa": "^8.0.1", + "inquirer": "^9.2.12" + }, + "devDependencies": { + "@types/inquirer": "9.0.7" + }, + "engines": { + "node": ">=18.16.0", + "npm": ">=8", + "pnpm": ">=7", + "yarn": ">=2" + }, + "publishConfig": { + "access": "public" + } +} diff --git a/create/src/action.ts b/create/src/action.ts new file mode 100644 index 0000000000..c896c72974 --- /dev/null +++ b/create/src/action.ts @@ -0,0 +1,118 @@ +#!/usr/bin/env node +import { existsSync, readdirSync } from 'node:fs' +import { resolve } from 'node:path' +import { execaCommand, execaCommandSync } from 'execa' +import inquirer from 'inquirer' +import { KNOWN_THEME_COMMANDS } from './config/index.js' +import { createPackageJson, generateTemplate } from './flow/index.js' +import { getLanguage } from './i18n/index.js' +import { + ensureDirExistSync, + getPackageManager, + getRegistry, + normalizeThemeName, +} from './utils/index.js' + +interface CreateOptions { + preset?: 'docs' | 'blog' | null + theme?: string +} + +export const mainAction = async ( + targetDir: string, + { preset = null, theme = '@vuepress/theme-default' }: CreateOptions, +): Promise => { + // get language + const { lang, locale } = await getLanguage() + + // get packageManager + const packageManager = await getPackageManager(locale.question.packageManager) + + // handle theme + const themePackageName = normalizeThemeName(theme) + + if (KNOWN_THEME_COMMANDS[themePackageName]) { + await execaCommandSync( + `${packageManager} ${KNOWN_THEME_COMMANDS[themePackageName]} ${targetDir}`, + { stdio: 'inherit' }, + ) + + return + } + + if (theme !== '@vuepress/theme-default') console.warn(locale.error.theme) + + // check presets + if (preset && !['docs', 'blog'].includes(preset)) + return console.log(locale.error.preset) + + // check if the user is a noob and warn him + if (!targetDir || (targetDir.startsWith('[') && targetDir.endsWith(']'))) + return console.log(locale.error.dirMissing(packageManager)) + + const targetDirPath = resolve(process.cwd(), targetDir) + + // check if the user is trying to cover his files + if (existsSync(targetDirPath) && readdirSync(targetDirPath).length) + return console.error(locale.error.dirNotEmpty(targetDir)) + + ensureDirExistSync(targetDirPath) + + /* + * Generate template + */ + + if (!preset) + preset = ( + await inquirer.prompt<{ preset: 'blog' | 'docs' }>([ + { + name: 'preset', + type: 'list', + message: locale.question.preset, + choices: ['blog', 'docs'], + }, + ]) + ).preset + + await createPackageJson(targetDir, packageManager, locale, preset) + await generateTemplate(targetDir, packageManager, lang, locale, preset) + + /* + * Install deps + */ + const registry = + packageManager === 'pnpm' ? '' : await getRegistry(packageManager, lang) + + console.log(locale.flow.install) + console.warn(locale.hint.install) + + execaCommandSync( + `${packageManager} install ${registry ? `--registry ${registry}` : ''}`, + { cwd: targetDirPath, stdout: 'inherit' }, + ) + + console.log(locale.hint.finish) + + /* + * Open dev server + */ + const { devServer } = await inquirer.prompt<{ devServer: boolean }>([ + { + name: 'devServer', + type: 'confirm', + message: locale.question.devServer, + default: true, + }, + ]) + + if (devServer) { + console.log(locale.flow.devServer) + + await execaCommand(`${packageManager} run docs:dev`, { + cwd: targetDir, + stdout: 'inherit', + }) + } else { + console.log(locale.hint.devServer(packageManager)) + } +} diff --git a/create/src/config/index.ts b/create/src/config/index.ts new file mode 100644 index 0000000000..50be8f5dfc --- /dev/null +++ b/create/src/config/index.ts @@ -0,0 +1,3 @@ +export const KNOWN_THEME_COMMANDS = { + hope: 'create-vuepress-theme-hope', +} diff --git a/create/src/flow/createPackageJson.ts b/create/src/flow/createPackageJson.ts new file mode 100644 index 0000000000..79e3334413 --- /dev/null +++ b/create/src/flow/createPackageJson.ts @@ -0,0 +1,98 @@ +import { writeFileSync } from 'node:fs' +import { join } from 'node:path' +import inquirer from 'inquirer' +import type { CreateLocaleOptions } from '../i18n/index.js' +import type { PackageManager } from '../utils/index.js' + +const PACKAGE_NAME_REG = + /^(?:@[a-z0-9-*~][a-z0-9-*._~]*\/)?[a-z0-9-~][a-z0-9-._~]*$/u + +const VERSION_REG = /^[0-9]+\.[0-9]+\.(?:[0-9]+|[0-9]+-[a-z]+\.[0-9])$/u + +interface PackageJsonAnswer { + name: string + version: string + description: string + license: string +} + +/** + * generate package.json + */ +export const createPackageJson = async ( + targetDir: string, + packageManager: PackageManager, + locale: CreateLocaleOptions, + preset: 'blog' | 'docs', +): Promise => { + const packageJsonPath = join(targetDir, 'package.json') + // TODO: Update it + const devDependencies = { + '@vuepress/client': '^2.0.0-rc.0', + '@vuepress/theme-default': '^2.0.0-rc.0', + 'vue': '^3.4.0', + 'vuepress': '^2.0.0-rc.0', + } + + if (preset === 'blog') { + devDependencies['@vuepress/core'] = '^2.0.0-rc.0' + devDependencies['vue-router'] = '^4.2.5' + } + + console.log(locale.flow.createPackage) + + const result = await inquirer.prompt([ + { + name: 'name', + type: 'input', + message: locale.question.name, + default: 'my-vuepress-site', + validate: (input: string): true | string => + PACKAGE_NAME_REG.exec(input) ? true : locale.error.name, + }, + { + name: 'version', + type: 'input', + message: locale.question.version, + default: '0.0.1', + validate: (input: string): true | string => + VERSION_REG.exec(input) ? true : locale.error.version, + }, + { + name: 'description', + type: 'input', + message: locale.question.description, + default: 'A VuePress project', + }, + { + name: 'license', + type: 'input', + message: locale.question.license, + default: 'MIT', + }, + ]) + + const packageContent = { + ...result, + type: 'module', + scripts: { + // eslint-disable-next-line @typescript-eslint/naming-convention + 'docs:build': `vuepress build src`, + // eslint-disable-next-line @typescript-eslint/naming-convention + 'docs:clean-dev': `vuepress dev src --clean-cache`, + // eslint-disable-next-line @typescript-eslint/naming-convention + 'docs:dev': `vuepress dev src`, + // eslint-disable-next-line @typescript-eslint/naming-convention + 'docs:update-package': `${ + packageManager === 'npm' ? 'npx' : `${packageManager} dlx` + } vp-update`, + }, + devDependencies, + } + + writeFileSync( + packageJsonPath, + `${JSON.stringify(packageContent, null, 2)}\n`, + { encoding: 'utf-8' }, + ) +} diff --git a/create/src/flow/generateTemplate.ts b/create/src/flow/generateTemplate.ts new file mode 100644 index 0000000000..c0fd37c483 --- /dev/null +++ b/create/src/flow/generateTemplate.ts @@ -0,0 +1,134 @@ +import { writeFileSync } from 'node:fs' +import { createRequire } from 'node:module' +import { dirname, join } from 'node:path' +import inquirer from 'inquirer' +import type { CreateLocaleOptions, Lang } from '../i18n/index.js' +import type { PackageManager } from '../utils/index.js' +import { copy, ensureDirExistSync } from '../utils/index.js' + +const templateFolder = join( + dirname( + createRequire(import.meta.url).resolve('create-vuepress/package.json'), + ), + './template', +) + +const getWorkflowContent = ( + packageManager: PackageManager, + lang: Lang, +): string => + ` +name: ${lang === '简体中文' ? '部署文档' : 'Deploy Docs'} + +on: + push: + branches: + # ${ + lang === '简体中文' + ? '确保这是你正在使用的分支名称' + : 'make sure this is the branch you are using' + } + - main + +permissions: + contents: write + +jobs: + deploy-gh-pages: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v3 + with: + fetch-depth: 0 + # ${ + lang === '简体中文' + ? '如果你文档需要 Git 子模块,取消注释下一行' + : 'if your docs needs submodules, uncomment the following line' + } + # submodules: true + +${ + packageManager === 'pnpm' + ? `\ + - name: ${lang === '简体中文' ? '安装 pnpm' : 'Install pnpm'} + uses: pnpm/action-setup@v2 + with: + run_install: true + version: 8 +` + : '' +} + + - name: ${lang === '简体中文' ? '设置 Node.js' : 'Setup Node.js'} + uses: actions/setup-node@v3 + with: + node-version: 20 + cache: ${packageManager} + +${ + packageManager !== 'pnpm' + ? `\ + - name: ${lang === '简体中文' ? '安装依赖' : 'Install Deps'} + run: ${ + packageManager === 'npm' + ? 'npm ci' + : `${packageManager} install --frozen-lockfile` + } +` + : '' +} + - name: ${lang === '简体中文' ? '构建文档' : 'Build Docs'} + env: + NODE_OPTIONS: --max_old_space_size=8192 + run: |- + ${packageManager} run docs:build + > src/.vuepress/dist/.nojekyll + + - name: ${lang === '简体中文' ? '部署文档' : 'Deploy Docs'} + uses: JamesIves/github-pages-deploy-action@v4 + with: + # ${ + lang === '简体中文' + ? '这是文档部署到的分支名称' + : 'This is the branch where the docs are deployed to' + } + branch: gh-pages + folder: src/.vuepress/dist +` + +export const generateTemplate = async ( + targetDir: string, + packageManager: PackageManager, + lang: Lang, + locale: CreateLocaleOptions, + preset: 'blog' | 'docs', +): Promise => { + const { workflow } = await inquirer.prompt<{ + workflow: boolean + }>([ + { + name: 'workflow', + type: 'confirm', + message: locale.question.workflow, + default: true, + }, + ]) + + console.log(locale.flow.generateTemplate) + + // copy template + copy(join(templateFolder, preset), join(targetDir, 'src')) + + if (workflow) { + const workflowDir = join(targetDir, '.github/workflows') + + ensureDirExistSync(workflowDir) + + writeFileSync( + join(workflowDir, 'deploy-docs.yml'), + getWorkflowContent(packageManager, lang), + { encoding: 'utf-8' }, + ) + } +} diff --git a/create/src/flow/index.ts b/create/src/flow/index.ts new file mode 100644 index 0000000000..b37e9a38c7 --- /dev/null +++ b/create/src/flow/index.ts @@ -0,0 +1,2 @@ +export * from './createPackageJson.js' +export * from './generateTemplate.js' diff --git a/create/src/i18n/en.ts b/create/src/i18n/en.ts new file mode 100644 index 0000000000..801a71035a --- /dev/null +++ b/create/src/i18n/en.ts @@ -0,0 +1,45 @@ +import type { PackageManager } from '../utils/index.js' +import type { CreateLocaleOptions } from './typings.js' + +export const en: CreateLocaleOptions = { + flow: { + getVersion: 'Getting latest version of deps...', + createPackage: 'Generating package.json...', + generateTemplate: 'Generating Template...', + install: 'Installing Deps...', + devServer: + "Staring dev server...\nAfter the dev server starts running, please visit the given server link ('localhost:8080' by default)", + }, + + question: { + i18n: 'Does the project need multiple languages?', + workflow: 'Do you need a GitHub workflow to deploy docs on GitHub pages?', + preset: 'What type of project do you want to create?', + packageManager: 'Choose package manager', + devServer: 'Would you like to preview template now?', + name: 'Your project name', + version: 'Your project version', + description: 'Your project description', + license: 'Your project license', + }, + + hint: { + install: + 'This may take a few minutes, please be patient.\nWe can not correctly output progress bar from child process, so the process may look stuck.', + finish: 'Successful Generated!', + devServer: (packageManager: PackageManager): string => + `Hint: You should execute "${packageManager} run docs:dev" to start dev server.`, + }, + + error: { + name: 'package name should only contain lowercase characters, numbers and dash', + version: "This version is not a valid one. Version should be like 'x.x.x'", + preset: 'preset (--preset) only support "doc" or "blog"', + theme: + 'Current theme is not supported yet, using @vuepress/theme-default instead.', + dirMissing: (packageManager: PackageManager): string => + `You should specific a folder name for your project, e.g.: "my-blog", "my-docs"\nFor example: "${packageManager} init vuepress my-docs"`, + dirNotEmpty: (dir: string) => + `Target folder "${dir}" is not empty, please choose an empty folder or delete files in it.`, + }, +} diff --git a/create/src/i18n/index.ts b/create/src/i18n/index.ts new file mode 100644 index 0000000000..9c15b74849 --- /dev/null +++ b/create/src/i18n/index.ts @@ -0,0 +1,32 @@ +import inquirer from 'inquirer' +import { en } from './en.js' +import type { CreateLocaleOptions, Lang } from './typings.js' +import { zh } from './zh.js' + +export * from './typings.js' + +const i18n: Record = { + 'english (US)': en, + '简体中文': zh, +} + +interface LanguageResult { + lang: Lang + locale: CreateLocaleOptions +} + +export const getLanguage = async (): Promise => { + const { language } = await inquirer.prompt<{ language: Lang }>([ + { + name: 'language', + type: 'list', + message: 'Select a language to display / 选择显示语言', + choices: ['english (US)', '简体中文'], + }, + ]) + + return { + lang: language, + locale: i18n[language], + } +} diff --git a/create/src/i18n/typings.ts b/create/src/i18n/typings.ts new file mode 100644 index 0000000000..b494c33bc6 --- /dev/null +++ b/create/src/i18n/typings.ts @@ -0,0 +1,40 @@ +import type { PackageManager } from '../utils/index.js' + +export type Lang = 'english (US)' | '简体中文' + +export interface CreateLocaleOptions { + flow: { + getVersion: string + createPackage: string + generateTemplate: string + install: string + devServer: string + } + + question: { + i18n: string + packageManager: string + name: string + version: string + description: string + license: string + workflow: string + preset: string + devServer: string + } + + hint: { + install: string + finish: string + devServer: (packageManager: PackageManager) => string + } + + error: { + name: string + version: string + preset: string + theme: string + dirMissing: (packageManager: PackageManager) => string + dirNotEmpty: (targetDir: string) => string + } +} diff --git a/create/src/i18n/zh.ts b/create/src/i18n/zh.ts new file mode 100644 index 0000000000..0cd5ab3d22 --- /dev/null +++ b/create/src/i18n/zh.ts @@ -0,0 +1,44 @@ +import type { PackageManager } from '../utils/index.js' +import type { CreateLocaleOptions } from './typings.js' + +export const zh: CreateLocaleOptions = { + flow: { + getVersion: '获取依赖的最新版本...', + createPackage: '生成 package.json...', + generateTemplate: '生成模板...', + install: '安装依赖...', + devServer: + "启动开发服务器...\n启动成功后,请在浏览器输入给出的开发服务器地址(默认为 'localhost:8080')", + }, + + question: { + packageManager: '选择包管理器', + i18n: '项目需要用到多语言么?', + workflow: '是否需要一个自动部署文档到 GitHub Pages 的工作流?', + preset: '你想要创建什么类型的项目?', + devServer: '是否想要现在启动 Demo 查看?', + name: '设置应用名称', + version: '设置应用版本号', + description: '设置应用描述', + license: '设置协议', + }, + + hint: { + install: + '这可能需要数分钟,请耐心等待.\n我们无法正确输出子进程的进度条,所以进程可能会看似未响应', + finish: '模板已成功生成!', + devServer: (packageManager: PackageManager): string => + `提示: 请使用 "${packageManager} run docs:dev" 命令启动开发服务器`, + }, + + error: { + name: '应用名称应只包含小写字母、数字和连接线 (-)', + version: "此版本无效,版本号应为 'x.x.x'", + preset: '预设 (--preset) 仅支持 doc 或 blog', + theme: '当前主题暂不支持,将使用 @vuepress/theme-default 代替', + dirMissing: (packageManager: PackageManager): string => + `你应该指定一个项目文件夹名称,例如 "my-blog", "my-docs"。\n例如: "${packageManager} init vuepress my-docs"`, + dirNotEmpty: (dir: string) => + `目标文件夹 "${dir}" 不为空,请选择一个空文件夹或者手动删除文件夹中的文件`, + }, +} diff --git a/create/src/index.ts b/create/src/index.ts new file mode 100644 index 0000000000..a554fe1716 --- /dev/null +++ b/create/src/index.ts @@ -0,0 +1,25 @@ +#!/usr/bin/env node +import { cac } from 'cac' +import { mainAction } from './action.js' +import { version } from './utils/index.js' + +const cli = cac('create-vuepress') + +cli + .command('[dir]', 'Generate a new vuepress project in [dir]') + .option('-t, --theme ', 'Theme to use') + .option('-p, --preset ', 'Preset to use, can be docs or blog') + .usage( + `\ +[dir] + +Generate vuepress template in dir.`, + ) + .example('vuepress-project') + .action(mainAction) + +cli.help() + +cli.version(version) + +cli.parse() diff --git a/create/src/utils/file.ts b/create/src/utils/file.ts new file mode 100644 index 0000000000..669faff096 --- /dev/null +++ b/create/src/utils/file.ts @@ -0,0 +1,49 @@ +import { + createReadStream, + createWriteStream, + mkdirSync, + readdirSync, + statSync, +} from 'node:fs' +import { dirname } from 'node:path' + +export const ensureDirExistSync = (dirPath: string): void => { + try { + readdirSync(dirPath) + } catch (err) { + try { + mkdirSync(dirPath, { recursive: true }) + } catch (err) { + // this is the case where the directory already exists but can not read, e.g.: D:\ + } + } +} + +export const copyFile = (srcFile: string, targetFile: string): void => { + const targetDir = dirname(targetFile) + + ensureDirExistSync(targetDir) + + const rs = createReadStream(srcFile) // create read stream + const ws = createWriteStream(targetFile) // create write stream + + rs.pipe(ws) +} + +export const copyDir = (srcDir: string, targetDir: string): void => { + ensureDirExistSync(targetDir) + + const files = readdirSync(srcDir, { withFileTypes: true }) + + files.forEach((file) => { + if (file.isFile()) + copyFile(`${srcDir}/${file.name}`, `${targetDir}/${file.name}`) + else if (file.isDirectory()) + copyDir(`${srcDir}/${file.name}`, `${targetDir}/${file.name}`) + }) +} + +export const copy = (src: string, target: string): void => { + if (statSync(src).isDirectory()) copyDir(src, target) + else if (statSync(src).isFile()) copyFile(src, target) +} diff --git a/create/src/utils/getPackageManager.ts b/create/src/utils/getPackageManager.ts new file mode 100644 index 0000000000..7610f92d88 --- /dev/null +++ b/create/src/utils/getPackageManager.ts @@ -0,0 +1,47 @@ +import { execaCommandSync } from 'execa' +import inquirer from 'inquirer' + +const checkPnpmInstalled = (): boolean => { + try { + return ( + execaCommandSync('pnpm --version', { stdio: 'ignore' }).exitCode === 0 + ) + } catch (e) { + return false + } +} + +const checkYarnInstalled = (): boolean => { + try { + return ( + execaCommandSync('yarn --version', { stdio: 'ignore' }).exitCode === 0 + ) + } catch (e) { + return false + } +} + +const availablePackageManagers = ['npm'] + +if (checkYarnInstalled()) availablePackageManagers.unshift('yarn') +if (checkPnpmInstalled()) availablePackageManagers.unshift('pnpm') + +export type PackageManager = 'npm' | 'yarn' | 'pnpm' + +export interface PackageManagerAnswer { + packageManager: PackageManager +} + +export const getPackageManager = async ( + message: string, +): Promise => + ( + await inquirer.prompt([ + { + name: 'packageManager', + type: 'list', + message, + choices: availablePackageManagers, + }, + ]) + ).packageManager diff --git a/create/src/utils/getRegistry.ts b/create/src/utils/getRegistry.ts new file mode 100644 index 0000000000..a1f9c3e0f3 --- /dev/null +++ b/create/src/utils/getRegistry.ts @@ -0,0 +1,58 @@ +import { execaCommandSync } from 'execa' +import inquirer from 'inquirer' +import type { Lang } from '../i18n/index.js' +import type { PackageManager } from './getPackageManager.js' + +interface RegistryAnswer { + registry: '国内镜像源' | '当前源' +} + +const NPM_MIRROR_REGISTRY = 'https://registry.npmmirror.com/' + +const getUserRegistry = ( + packageManager: PackageManager, + isYarnModern: boolean, +): string => + execaCommandSync( + `${packageManager} config get ${ + isYarnModern ? 'npmRegistryServer' : 'registry' + }`, + ).stdout + +export const getRegistry = async ( + packageManager: PackageManager, + lang: Lang, +): Promise => { + const isYarnModern = + packageManager === 'yarn' && + !execaCommandSync('yarn --version').stdout.startsWith('1') + + const userRegistry = getUserRegistry(packageManager, isYarnModern) + + if (/https:\/\/registry\.npm\.taobao\.org\/?/.test(userRegistry)) { + console.error( + 'npm.taobao.org is no longer available, resetting it to npmmirror.com', + ) + + execaCommandSync( + `${packageManager} config set ${ + isYarnModern ? 'npmRegistryServer' : 'registry' + }} ${NPM_MIRROR_REGISTRY}`, + ) + } + + if (lang === '简体中文') { + const { registry } = await inquirer.prompt([ + { + name: 'registry', + type: 'list', + message: '选择你想使用的源', + choices: ['国内镜像源', '当前源'], + }, + ]) + + return registry === '国内镜像源' ? NPM_MIRROR_REGISTRY : userRegistry + } + + return userRegistry +} diff --git a/create/src/utils/index.ts b/create/src/utils/index.ts new file mode 100644 index 0000000000..68870aa33a --- /dev/null +++ b/create/src/utils/index.ts @@ -0,0 +1,5 @@ +export * from './file.js' +export * from './getPackageManager.js' +export * from './normalizeThemeName.js' +export * from './getRegistry.js' +export * from './version.js' diff --git a/create/src/utils/normalizeThemeName.ts b/create/src/utils/normalizeThemeName.ts new file mode 100644 index 0000000000..95d7d7aac5 --- /dev/null +++ b/create/src/utils/normalizeThemeName.ts @@ -0,0 +1,25 @@ +const THEME_PREFIX = 'vuepress-theme-' + +/** + * Normalize theme name + */ +export const normalizeThemeName = (name: string): string => { + // scoped package pattern + const scopedMatch = name.match(/^@(.*)\/(.*)$/) + + // handle non-scoped package + if (scopedMatch === null) + return name.startsWith(THEME_PREFIX) ? name : `${THEME_PREFIX}${name}` + + // handle scoped package + const [, reqOrg, reqName] = scopedMatch + + // handle @vuepress/ themes + if (reqOrg === 'vuepress') + return reqName.startsWith('theme-') ? name : `@vuepress/theme-${reqName}` + + // handle other org + return reqName.startsWith(THEME_PREFIX) + ? name + : `@${reqOrg}/${THEME_PREFIX}${reqName}` +} diff --git a/create/src/utils/version.ts b/create/src/utils/version.ts new file mode 100644 index 0000000000..752b8c3014 --- /dev/null +++ b/create/src/utils/version.ts @@ -0,0 +1,7 @@ +import { createRequire } from 'node:module' + +export const version = ( + createRequire(import.meta.url)('create-vuepress/package.json') as { + version: string + } +).version diff --git a/create/template/blog/.vuepress/blog-plugin.js b/create/template/blog/.vuepress/blog-plugin.js new file mode 100644 index 0000000000..f069e2e569 --- /dev/null +++ b/create/template/blog/.vuepress/blog-plugin.js @@ -0,0 +1,109 @@ +import { createPage } from '@vuepress/core' + +const slugify = (name) => + name + .replace(/[ _]/g, '-') + .replace(/[:?*|\\/<>]/g, '') + .toLowerCase() + +const generateCategory = async (app, name) => { + const map = {} + + await app.pages.map(async (page) => { + const value = page.frontmatter[name] + + await (Array.isArray(value) ? value : [value]).map(async (item) => { + if (item && !map[item]) { + const itemPath = `/${name}/${slugify(item)}/` + + map[item] = { + path: itemPath, + keys: [], + } + + app.pages.push( + await createPage(app, { + path: itemPath, + frontmatter: { + title: `${name} > ${item}`, + key: item, + layout: name, + sidebar: false, + }, + }), + ) + } + + map[item].keys.push(page.key) + }) + }) + + app.pages.push( + await createPage(app, { + path: `/${name}/`, + frontmatter: { + title: name, + layout: name, + sidebar: false, + }, + }), + ) + + await app.writeTemp( + `blog/${name}.js`, + `\ +export const map = ${JSON.stringify(map)}; +`, + ) +} + +const generateType = async ( + app, + name, + { filter = () => true, sorter = () => 0 }, +) => { + app.pages.push( + await createPage(app, { + path: `/${name}/`, + frontmatter: { + title: name, + layout: name, + sidebar: false, + }, + }), + ) + + const keys = app.pages.filter(filter).map(({ key }) => key) + + await app.writeTemp( + `blog/${name}.js`, + `\ +export const keys = ${JSON.stringify(keys)}; +`, + ) +} + +export const simpleBlogPlugin = ({ + filter = () => true, + getInfo, + category = [], + type = [], +}) => ({ + name: 'simple-blog-plugin', + + onInitialized: async (app) => { + // inject meta information + app.pages.filter(filter).forEach((page) => { + page.routeMeta = { + ...page.routeMeta, + ...getInfo(page), + } + }) + + // generate pages and temp files + await Promise.all([ + ...category.map((name) => generateCategory(app, name)), + ...type.map(({ key, ...options }) => generateType(app, key, options)), + ]) + }, +}) diff --git a/create/template/blog/.vuepress/client.js b/create/template/blog/.vuepress/client.js new file mode 100644 index 0000000000..7b2c000713 --- /dev/null +++ b/create/template/blog/.vuepress/client.js @@ -0,0 +1,15 @@ +import { defineClientConfig } from '@vuepress/client' +import Article from './layouts/Article.vue' +import Category from './layouts/Category.vue' +import Tag from './layouts/Tag.vue' +import Timeline from './layouts/Timeline.vue' + +export default defineClientConfig({ + // we provide some blog layouts + layouts: { + Article, + Category, + Tag, + Timeline, + }, +}) diff --git a/create/template/blog/.vuepress/components/ArticleList.vue b/create/template/blog/.vuepress/components/ArticleList.vue new file mode 100644 index 0000000000..6f19d76f9b --- /dev/null +++ b/create/template/blog/.vuepress/components/ArticleList.vue @@ -0,0 +1,134 @@ + + + + + diff --git a/create/template/blog/.vuepress/config.js b/create/template/blog/.vuepress/config.js new file mode 100644 index 0000000000..f8c00b362f --- /dev/null +++ b/create/template/blog/.vuepress/config.js @@ -0,0 +1,88 @@ +import { defaultTheme } from '@vuepress/theme-default' +import { defineUserConfig } from 'vuepress' +import { simpleBlogPlugin } from './blog-plugin' + +export default defineUserConfig({ + lang: 'en-US', + + title: 'VuePress', + description: 'My first VuePress Site', + + theme: defaultTheme({ + logo: 'https://vuejs.press/images/hero.png', + + navbar: [ + '/', + { + text: 'Article', + link: '/article/', + }, + { + text: 'Category', + link: '/category/', + }, + { + text: 'Tag', + link: '/tag/', + }, + { + text: 'Timeline', + link: '/timeline/', + }, + ], + }), + + plugins: [ + simpleBlogPlugin({ + // only files under posts are articles + filter: ({ filePathRelative }) => + filePathRelative ? filePathRelative.startsWith('posts/') : false, + + // getting article info + getInfo: ({ frontmatter, title }) => ({ + title, + author: frontmatter.author || '', + date: frontmatter.date || null, + category: frontmatter.category || [], + tag: frontmatter.tag || [], + excerpt: frontmatter.excerpt || '', + }), + + category: ['category', 'tag'], + + type: [ + { + key: 'article', + // remove archive articles + filter: (page) => !page.frontmatter.archive, + + sorter: (pageA, pageB) => { + if (pageA.frontmatter.sticky && pageB.frontmatter.sticky) + return pageB.frontmatter.sticky - pageA.frontmatter.sticky + + if (pageA.frontmatter.sticky && !pageB.frontmatter.sticky) return -1 + + if (!pageA.frontmatter.sticky && pageB.frontmatter.sticky) return 1 + + if (!pageB.frontmatter.date) return 1 + if (!pageA.frontmatter.date) return -1 + + return ( + new Date(pageB.frontmatter.date).getTime() - + new Date(pageA.frontmatter.date).getTime() + ) + }, + }, + { + key: 'timeline', + // only article with date should be added to timeline + filter: (page) => page.frontmatter.date instanceof Date, + // sort pages with time + sorter: (pageA, pageB) => + new Date(pageB.frontmatter.date).getTime() - + new Date(pageA.frontmatter.date).getTime(), + }, + ], + }), + ], +}) diff --git a/create/template/blog/.vuepress/layouts/Article.vue b/create/template/blog/.vuepress/layouts/Article.vue new file mode 100644 index 0000000000..6ca19a4a88 --- /dev/null +++ b/create/template/blog/.vuepress/layouts/Article.vue @@ -0,0 +1,22 @@ + + + diff --git a/create/template/blog/.vuepress/layouts/Category.vue b/create/template/blog/.vuepress/layouts/Category.vue new file mode 100644 index 0000000000..0bcc135395 --- /dev/null +++ b/create/template/blog/.vuepress/layouts/Category.vue @@ -0,0 +1,111 @@ + + + + + diff --git a/create/template/blog/.vuepress/layouts/Tag.vue b/create/template/blog/.vuepress/layouts/Tag.vue new file mode 100644 index 0000000000..65df0debd1 --- /dev/null +++ b/create/template/blog/.vuepress/layouts/Tag.vue @@ -0,0 +1,111 @@ + + + + + diff --git a/create/template/blog/.vuepress/layouts/Timeline.vue b/create/template/blog/.vuepress/layouts/Timeline.vue new file mode 100644 index 0000000000..b93bd27ea3 --- /dev/null +++ b/create/template/blog/.vuepress/layouts/Timeline.vue @@ -0,0 +1,30 @@ + + + + + diff --git a/create/template/blog/README.md b/create/template/blog/README.md new file mode 100644 index 0000000000..49f0744e02 --- /dev/null +++ b/create/template/blog/README.md @@ -0,0 +1,33 @@ +--- +home: true +title: Home +heroImage: https://vuejs.press/images/hero.png +actions: + - text: Get Started + link: /getting-started.html + type: primary + + - text: Introduction + link: https://vuejs.press/guide/introduction.html + type: secondary + +features: + - title: Simplicity First + details: Minimal setup with markdown-centered project structure helps you focus on writing. + - title: Vue-Powered + details: Enjoy the dev experience of Vue, use Vue components in markdown, and develop custom themes with Vue. + - title: Performant + details: VuePress generates pre-rendered static HTML for each page, and runs as an SPA once a page is loaded. + - title: Themes + details: Providing a default theme out of the box. You can also choose a community theme or create your own one. + - title: Plugins + details: Flexible plugin API, allowing plugins to provide lots of plug-and-play features for your site. + - title: Bundlers + details: Default bundler is Vite, while Webpack is also supported. Choose the one you like! + +footer: MIT Licensed | Copyright © 2018-present VuePress Community +--- + +This is the content of home page. Check [Home Page Docs][default-theme-home] for more details. + +[default-theme-home]: https://vuejs.press/reference/default-theme/frontmatter.html#home-page diff --git a/create/template/blog/get-started.md b/create/template/blog/get-started.md new file mode 100644 index 0000000000..0b7b0319a9 --- /dev/null +++ b/create/template/blog/get-started.md @@ -0,0 +1,46 @@ +# Get Started + +This is a normal page, which contains VuePress basics. + +## Pages + +You can add markdown files in your vuepress directory, every markdown file will be converted to a page in your site. + +See [routing][] for more details. + +## Content + +Every markdown file [will be rendered to HTML, then converted to a Vue SFC][content]. + +VuePress support basic markdown syntax and [some extensions][synatex-extensions], you can also [use Vue features][vue-feature] in it. + +## Configuration + +VuePress use a `.vuepress/config.js`(or .ts) file as [site configuration][config], you can use it to config your site. + +For [client side configuration][client-config], you can create `.vuepress/client.js`(or .ts). + +Meanwhile, you can also add configuration per page with [frontmatter][]. + +## Layouts and customization + +Here are common configuration controlling layout of `@vuepress/theme-default`: + +- [navbar][] +- [sidebar][] + +Check [default theme docs][default-theme] for full reference. + +You can [add extra style][style] with `.vuepress/styles/index.scss` file. + +[routing]: https://vuejs.press/guide/page.html#routing +[content]: https://vuejs.press/guide/page.html#content +[synatex-extensions]: https://vuejs.press/guide/markdown.html#syntax-extensions +[vue-feature]: https://vuejs.press/guide/markdown.html#using-vue-in-markdown +[config]: https://vuejs.press/guide/configuration.html#client-config-file +[client-config]: https://vuejs.press/guide/configuration.html#client-config-file +[frontmatter]: https://vuejs.press/guide/page.html#frontmatter +[navbar]: https://vuejs.press/reference/default-theme/config.html#navbar +[sidebar]: https://vuejs.press/reference/default-theme/config.html#sidebar +[default-theme]: https://vuejs.press/reference/default-theme/ +[style]: https://vuejs.press/reference/default-theme/styles.html#style-file diff --git a/create/template/blog/posts/archive1.md b/create/template/blog/posts/archive1.md new file mode 100644 index 0000000000..fb583eaddc --- /dev/null +++ b/create/template/blog/posts/archive1.md @@ -0,0 +1,18 @@ +--- +date: 1998-01-01 +category: + - History +tag: + - WWI +archive: true +--- + +# Archive Article1 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/archive2.md b/create/template/blog/posts/archive2.md new file mode 100644 index 0000000000..087ad8a8cc --- /dev/null +++ b/create/template/blog/posts/archive2.md @@ -0,0 +1,18 @@ +--- +date: 1998-01-02 +category: + - History +tag: + - WWII +archive: true +--- + +# Archive Article2 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article1.md b/create/template/blog/posts/article1.md new file mode 100644 index 0000000000..35bdbeee4b --- /dev/null +++ b/create/template/blog/posts/article1.md @@ -0,0 +1,18 @@ +--- +date: 2022-01-01 +category: + - CategoryA +tag: + - tag A + - tag B +--- + +# Article 1 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article10.md b/create/template/blog/posts/article10.md new file mode 100644 index 0000000000..992b3b267f --- /dev/null +++ b/create/template/blog/posts/article10.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-10 +category: + - CategoryA + - CategoryB +tag: + - tag C + - tag D +--- + +# Article 10 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article11.md b/create/template/blog/posts/article11.md new file mode 100644 index 0000000000..4d4038bf6f --- /dev/null +++ b/create/template/blog/posts/article11.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-11 +category: + - CategoryA + - CategoryB +tag: + - tag C + - tag D +--- + +# Article 11 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article12.md b/create/template/blog/posts/article12.md new file mode 100644 index 0000000000..9d32cf8070 --- /dev/null +++ b/create/template/blog/posts/article12.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-12 +category: + - CategoryA + - CategoryB +tag: + - tag C + - tag D +--- + +# Article 12 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article2.md b/create/template/blog/posts/article2.md new file mode 100644 index 0000000000..e995e373a1 --- /dev/null +++ b/create/template/blog/posts/article2.md @@ -0,0 +1,18 @@ +--- +date: 2022-01-02 +category: + - CategoryA +tag: + - tag A + - tag B +--- + +# Article 2 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article3.md b/create/template/blog/posts/article3.md new file mode 100644 index 0000000000..28a8727572 --- /dev/null +++ b/create/template/blog/posts/article3.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-03 +category: + - CategoryA + - CategoryB +tag: + - tag A + - tag B +--- + +# Article 3 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article4.md b/create/template/blog/posts/article4.md new file mode 100644 index 0000000000..ac868755e5 --- /dev/null +++ b/create/template/blog/posts/article4.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-04 +category: + - CategoryA + - CategoryB +tag: + - tag A + - tag B +--- + +# Article 4 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article5.md b/create/template/blog/posts/article5.md new file mode 100644 index 0000000000..3193aac23d --- /dev/null +++ b/create/template/blog/posts/article5.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-05 +category: + - CategoryA + - CategoryB +tag: + - tag A + - tag B +--- + +# Article 5 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article6.md b/create/template/blog/posts/article6.md new file mode 100644 index 0000000000..fd7fb69c5b --- /dev/null +++ b/create/template/blog/posts/article6.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-06 +category: + - CategoryA + - CategoryB +tag: + - tag A + - tag B +--- + +# Article 6 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article7.md b/create/template/blog/posts/article7.md new file mode 100644 index 0000000000..a1095b7c6c --- /dev/null +++ b/create/template/blog/posts/article7.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-07 +category: + - CategoryA + - CategoryB +tag: + - tag C + - tag D +--- + +# Article 7 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article8.md b/create/template/blog/posts/article8.md new file mode 100644 index 0000000000..f142fd615f --- /dev/null +++ b/create/template/blog/posts/article8.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-08 +category: + - CategoryA + - CategoryB +tag: + - tag C + - tag D +--- + +# Article 8 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/article9.md b/create/template/blog/posts/article9.md new file mode 100644 index 0000000000..0b3a2d5df3 --- /dev/null +++ b/create/template/blog/posts/article9.md @@ -0,0 +1,19 @@ +--- +date: 2022-01-09 +category: + - CategoryA + - CategoryB +tag: + - tag C + - tag D +--- + +# Article 9 + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/sticky.md b/create/template/blog/posts/sticky.md new file mode 100644 index 0000000000..42869248d2 --- /dev/null +++ b/create/template/blog/posts/sticky.md @@ -0,0 +1,19 @@ +--- +date: 2021-01-01 +category: + - CategoryC +tag: + - tag E +sticky: true +excerpt:

A sticky article demo.

+--- + +# Sticky Article + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/blog/posts/sticky2.md b/create/template/blog/posts/sticky2.md new file mode 100644 index 0000000000..861ba9eb36 --- /dev/null +++ b/create/template/blog/posts/sticky2.md @@ -0,0 +1,22 @@ +--- +date: 2020-01-01 +category: + - CategoryC +tag: + - tag E +sticky: 10 +--- + +# Sticky Article with Higher Priority + +Excerpt information which is added manually. + + + +## Heading 2 + +Here is the content. + +### Heading 3 + +Here is the content. diff --git a/create/template/docs/.vuepress/config.js b/create/template/docs/.vuepress/config.js new file mode 100644 index 0000000000..5d3c5cbf93 --- /dev/null +++ b/create/template/docs/.vuepress/config.js @@ -0,0 +1,15 @@ +import { defaultTheme } from '@vuepress/theme-default' +import { defineUserConfig } from 'vuepress' + +export default defineUserConfig({ + lang: 'en-US', + + title: 'VuePress', + description: 'My first VuePress Site', + + theme: defaultTheme({ + logo: 'https://vuejs.press/images/hero.png', + + navbar: ['/', '/get-started'], + }), +}) diff --git a/create/template/docs/README.md b/create/template/docs/README.md new file mode 100644 index 0000000000..49f0744e02 --- /dev/null +++ b/create/template/docs/README.md @@ -0,0 +1,33 @@ +--- +home: true +title: Home +heroImage: https://vuejs.press/images/hero.png +actions: + - text: Get Started + link: /getting-started.html + type: primary + + - text: Introduction + link: https://vuejs.press/guide/introduction.html + type: secondary + +features: + - title: Simplicity First + details: Minimal setup with markdown-centered project structure helps you focus on writing. + - title: Vue-Powered + details: Enjoy the dev experience of Vue, use Vue components in markdown, and develop custom themes with Vue. + - title: Performant + details: VuePress generates pre-rendered static HTML for each page, and runs as an SPA once a page is loaded. + - title: Themes + details: Providing a default theme out of the box. You can also choose a community theme or create your own one. + - title: Plugins + details: Flexible plugin API, allowing plugins to provide lots of plug-and-play features for your site. + - title: Bundlers + details: Default bundler is Vite, while Webpack is also supported. Choose the one you like! + +footer: MIT Licensed | Copyright © 2018-present VuePress Community +--- + +This is the content of home page. Check [Home Page Docs][default-theme-home] for more details. + +[default-theme-home]: https://vuejs.press/reference/default-theme/frontmatter.html#home-page diff --git a/create/template/docs/get-started.md b/create/template/docs/get-started.md new file mode 100644 index 0000000000..0b7b0319a9 --- /dev/null +++ b/create/template/docs/get-started.md @@ -0,0 +1,46 @@ +# Get Started + +This is a normal page, which contains VuePress basics. + +## Pages + +You can add markdown files in your vuepress directory, every markdown file will be converted to a page in your site. + +See [routing][] for more details. + +## Content + +Every markdown file [will be rendered to HTML, then converted to a Vue SFC][content]. + +VuePress support basic markdown syntax and [some extensions][synatex-extensions], you can also [use Vue features][vue-feature] in it. + +## Configuration + +VuePress use a `.vuepress/config.js`(or .ts) file as [site configuration][config], you can use it to config your site. + +For [client side configuration][client-config], you can create `.vuepress/client.js`(or .ts). + +Meanwhile, you can also add configuration per page with [frontmatter][]. + +## Layouts and customization + +Here are common configuration controlling layout of `@vuepress/theme-default`: + +- [navbar][] +- [sidebar][] + +Check [default theme docs][default-theme] for full reference. + +You can [add extra style][style] with `.vuepress/styles/index.scss` file. + +[routing]: https://vuejs.press/guide/page.html#routing +[content]: https://vuejs.press/guide/page.html#content +[synatex-extensions]: https://vuejs.press/guide/markdown.html#syntax-extensions +[vue-feature]: https://vuejs.press/guide/markdown.html#using-vue-in-markdown +[config]: https://vuejs.press/guide/configuration.html#client-config-file +[client-config]: https://vuejs.press/guide/configuration.html#client-config-file +[frontmatter]: https://vuejs.press/guide/page.html#frontmatter +[navbar]: https://vuejs.press/reference/default-theme/config.html#navbar +[sidebar]: https://vuejs.press/reference/default-theme/config.html#sidebar +[default-theme]: https://vuejs.press/reference/default-theme/ +[style]: https://vuejs.press/reference/default-theme/styles.html#style-file diff --git a/create/tsconfig.build.json b/create/tsconfig.build.json new file mode 100644 index 0000000000..c00ebcd6b4 --- /dev/null +++ b/create/tsconfig.build.json @@ -0,0 +1,9 @@ +{ + "extends": "../tsconfig.build.json", + "compilerOptions": { + "rootDir": "./src", + "outDir": "./lib", + "baseUrl": "." + }, + "include": ["./src"] +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 7d08a93c3a..4c66cf403e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -72,6 +72,22 @@ importers: specifier: ^1.1.0 version: 1.1.0(@types/node@20.10.5) + create: + dependencies: + cac: + specifier: ^6.7.14 + version: 6.7.14 + execa: + specifier: ^8.0.1 + version: 8.0.1 + inquirer: + specifier: ^9.2.12 + version: 9.2.12 + devDependencies: + '@types/inquirer': + specifier: 9.0.7 + version: 9.0.7 + plugins/plugin-active-header-links: dependencies: '@vuepress/client': @@ -2525,7 +2541,6 @@ packages: engines: {node: '>= 0.4'} dependencies: call-bind: 1.0.5 - dev: true /@mdit-vue/plugin-component@1.0.0: resolution: {integrity: sha512-ZXsJwxkG5yyTHARIYbR74cT4AZ0SfMokFFjiHYCbypHIeYWgJhso4+CZ8+3V9EWFG3EHlGoKNGqKp9chHnqntQ==} @@ -3145,6 +3160,13 @@ packages: resolution: {integrity: sha512-UP28RddqY8xcU0SCEp9YKutQICXpaAq9N8U2klqF5hegGha7KzTOL8EdhIIV3bOSGBzjEpN9bU/d+nNZBdJYVw==} dev: false + /@types/inquirer@9.0.7: + resolution: {integrity: sha512-Q0zyBupO6NxGRZut/JdmqYKOnN95Eg5V8Csg3PGKkP+FnvsUZx1jAyK7fztIszxxMuoBA6E3KXWvdZVXIpx60g==} + dependencies: + '@types/through': 0.0.33 + rxjs: 7.8.1 + dev: true + /@types/json-schema@7.0.15: resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} @@ -3216,6 +3238,12 @@ packages: resolution: {integrity: sha512-dn1l8LaMea/IjDoHNd9J52uBbInB796CDffS6VdIxvqYCPSG0V0DzHp76GpaWnlhg88uYyPbXCDIowa86ybd5A==} dev: true + /@types/through@0.0.33: + resolution: {integrity: sha512-HsJ+z3QuETzP3cswwtzt2vEIiHBk/dCcHGhbmG5X3ecnwFD/lPrMpliGXxSCg03L9AhrdwA4Oz/qfspkDW+xGQ==} + dependencies: + '@types/node': 20.10.5 + dev: true + /@types/trusted-types@2.0.7: resolution: {integrity: sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==} dev: false @@ -3827,7 +3855,6 @@ packages: engines: {node: '>=8'} dependencies: type-fest: 0.21.3 - dev: true /ansi-escapes@6.2.0: resolution: {integrity: sha512-kzRaCqXnpzWs+3z5ABPQiVke+iq0KXkHo8xiWV4RPTi5Yli0l97BEQuhXV1s7+aSU/fu1kUuxgS4MsQ0fRuygw==} @@ -3839,7 +3866,6 @@ packages: /ansi-regex@5.0.1: resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} engines: {node: '>=8'} - dev: true /ansi-regex@6.0.1: resolution: {integrity: sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==} @@ -4054,7 +4080,6 @@ packages: buffer: 5.7.1 inherits: 2.0.4 readable-stream: 3.6.2 - dev: true /bl@5.1.0: resolution: {integrity: sha512-tv1ZJHLfTDnXE6tMHv73YgSJaWR2AFuPwMntBe7XL/GBFHnT0CLnsHMogfk5+GzCDC5ZWarSCYaIGATZt9dNsQ==} @@ -4104,7 +4129,6 @@ packages: dependencies: base64-js: 1.5.1 ieee754: 1.2.1 - dev: true /buffer@6.0.3: resolution: {integrity: sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA==} @@ -4130,7 +4154,6 @@ packages: /cac@6.7.14: resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} engines: {node: '>=8'} - dev: true /cacache@18.0.1: resolution: {integrity: sha512-g4Uf2CFZPaxtJKre6qr4zqLDOOPU7bNVhWjlNhvzc51xaTOx2noMOLhfFkTAqwtrAZAKQUuDfyjitzilpA8WsQ==} @@ -4213,7 +4236,6 @@ packages: /chardet@0.7.0: resolution: {integrity: sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==} - dev: true /check-error@1.0.3: resolution: {integrity: sha512-iKEoDYaRmd1mxM90a2OEfWhjsjPpYPuQ+lMYsoxB126+t8fw7ySEO48nmDg5COTjxDI65/Y2OWpeEHk3ZOe8zg==} @@ -4266,7 +4288,6 @@ packages: engines: {node: '>=8'} dependencies: restore-cursor: 3.1.0 - dev: true /cli-cursor@4.0.0: resolution: {integrity: sha512-VGtlMu3x/4DOtIUwEkRezxUZ2lBacNJCHash0N0WeZDBS+7Ux1dm3XWAgWYxLJFMMdOeXMHXorshEFhbMSGelg==} @@ -4289,7 +4310,6 @@ packages: /cli-width@4.1.0: resolution: {integrity: sha512-ouuZd4/dm2Sw5Gmqy6bGyNNNe1qt9RpmxveLSO7KcgsTnU7RXfsw+/bukWGo1abgBiMAic068rclZsO4IWmmxQ==} engines: {node: '>= 12'} - dev: true /cliui@8.0.1: resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==} @@ -4312,7 +4332,6 @@ packages: /clone@1.0.4: resolution: {integrity: sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg==} engines: {node: '>=0.8'} - dev: true /cmd-shim@6.0.2: resolution: {integrity: sha512-+FFYbB0YLaAkhkcrjkyNLYDiOsFSfRjwjY19LXk/psmMx1z00xlCv7hhQoTGXXIKi+YXHL/iiFo8NqMVQX9nOw==} @@ -4658,7 +4677,6 @@ packages: resolution: {integrity: sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A==} dependencies: clone: 1.0.4 - dev: true /define-data-property@1.1.1: resolution: {integrity: sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ==} @@ -4755,7 +4773,6 @@ packages: /emoji-regex@8.0.0: resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} - dev: true /emoji-regex@9.2.2: resolution: {integrity: sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==} @@ -4919,7 +4936,6 @@ packages: /escape-string-regexp@5.0.0: resolution: {integrity: sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==} engines: {node: '>=12'} - dev: true /eslint-compat-utils@0.1.2(eslint@8.56.0): resolution: {integrity: sha512-Jia4JDldWnFNIru1Ehx1H5s9/yxiRHY/TimCuUc0jNexew3cF1gI6CYZil1ociakfWO3rRqFjl1mskBblB3RYg==} @@ -5298,7 +5314,6 @@ packages: chardet: 0.7.0 iconv-lite: 0.4.24 tmp: 0.0.33 - dev: true /fast-deep-equal@3.1.3: resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} @@ -5339,7 +5354,6 @@ packages: dependencies: escape-string-regexp: 5.0.0 is-unicode-supported: 1.3.0 - dev: true /file-entry-cache@6.0.1: resolution: {integrity: sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==} @@ -5851,7 +5865,6 @@ packages: engines: {node: '>=0.10.0'} dependencies: safer-buffer: 2.1.2 - dev: true /iconv-lite@0.6.3: resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} @@ -5943,7 +5956,6 @@ packages: string-width: 4.2.3 strip-ansi: 6.0.1 wrap-ansi: 6.2.0 - dev: true /internal-slot@1.0.6: resolution: {integrity: sha512-Xj6dv+PsbtwyPpEflsejS+oIZxmMlV44zAhG479uYu89MsjcYOhCFnNyKrkJrihbsiasQyY0afoCl/9BLR65bg==} @@ -6028,7 +6040,6 @@ packages: /is-fullwidth-code-point@3.0.0: resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} engines: {node: '>=8'} - dev: true /is-fullwidth-code-point@4.0.0: resolution: {integrity: sha512-O4L094N2/dZ7xqVdrXhh9r1KODPJpFms8B5sGdJLPy664AgvXsreZUyCQQNItZRDlYug4xStLjNp/sz3HvBowQ==} @@ -6051,7 +6062,6 @@ packages: /is-interactive@1.0.0: resolution: {integrity: sha512-2HvIEKRoqS62guEC+qBjpvRubdX910WCMuJTZ+I9yvqKU2/12eSL549HMwtabb4oupdj2sMP50k+XJfB/8JE6w==} engines: {node: '>=8'} - dev: true /is-interactive@2.0.0: resolution: {integrity: sha512-qP1vozQRI+BMOPcjFzrjXuQvdak2pHNUMZoeG2eRbiSqyvbEf/wQtEOTOX1guk6E3t36RkaqiSt8A/6YElNxLQ==} @@ -6175,7 +6185,6 @@ packages: /is-unicode-supported@0.1.0: resolution: {integrity: sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw==} engines: {node: '>=10'} - dev: true /is-unicode-supported@1.3.0: resolution: {integrity: sha512-43r2mRvz+8JRIKnWJ+3j8JtjRKZ6GmjzfaE/qiBJnikNnYv/6bagRJ1kUhNk8R5EX/GkobD+r+sfxCPJsiKBLQ==} @@ -6596,7 +6605,6 @@ packages: dependencies: chalk: 4.1.2 is-unicode-supported: 0.1.0 - dev: true /log-symbols@5.1.0: resolution: {integrity: sha512-l0x2DvrW294C9uDCoQe1VSU4gf529FkSZ6leBl4TiqZH/e+0R7hSfHQBNut2mNygDgHwvYHfFLn6Oxb3VWj2rA==} @@ -6942,7 +6950,6 @@ packages: /mute-stream@1.0.0: resolution: {integrity: sha512-avsJQhyd+680gKXyG/sQc0nXaC6rBkPOfyHYcFb9+hdkqQkR9bdnkJ0AMZhke0oesPqIO+mFFJ+IdBc7mst4IA==} engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0} - dev: true /nanoid@3.3.7: resolution: {integrity: sha512-eSRppjcPIatRIMC1U6UngP8XFcz8MQWGQdt1MTBQ7NaAmvXDfvNxbvWV3x2y6CdEUciCSsDHDQZbhYaB8QEo2g==} @@ -7220,7 +7227,6 @@ packages: log-symbols: 4.1.0 strip-ansi: 6.0.1 wcwidth: 1.0.1 - dev: true /ora@7.0.1: resolution: {integrity: sha512-0TUxTiFJWv+JnjWm4o9yvuskpEJLXTcng8MJuKd+SzAzp2o+OP3HWqNhB4OdJRt1Vsd9/mR0oyaEYlOnL7XIRw==} @@ -7240,7 +7246,6 @@ packages: /os-tmpdir@1.0.2: resolution: {integrity: sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g==} engines: {node: '>=0.10.0'} - dev: true /p-limit@2.3.0: resolution: {integrity: sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==} @@ -7818,7 +7823,6 @@ packages: dependencies: onetime: 5.1.2 signal-exit: 3.0.7 - dev: true /restore-cursor@4.0.0: resolution: {integrity: sha512-I9fPXU9geO9bHOt9pHHOhOkYerIMsmVaWB0rA2AI9ERh/+x/i7MV5HKBNrg+ljO5eoPVgCcnFuRjJ9uH6I/3eg==} @@ -7900,7 +7904,6 @@ packages: /run-async@3.0.0: resolution: {integrity: sha512-540WwVDOMxA6dN6We19EcT9sc3hkXPw5mzRNGM3FkdN/vtE9NFvj5lFAPNwUDmJjXidm3v7TC1cTE7t17Ulm1Q==} engines: {node: '>=0.12.0'} - dev: true /run-parallel@1.2.0: resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} @@ -7911,7 +7914,6 @@ packages: resolution: {integrity: sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==} dependencies: tslib: 2.6.2 - dev: true /safe-array-concat@1.0.1: resolution: {integrity: sha512-6XbUAseYE2KtOuGueyeobCySj9L4+66Tn6KQMOPQJrAJEowYKW/YR/MGJZl7FdydUdaFu4LYyDZjxf4/Nmo23Q==} @@ -7934,7 +7936,6 @@ packages: /safer-buffer@2.1.2: resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} - dev: true /sass-loader@13.3.2(sass@1.69.6)(webpack@5.89.0): resolution: {integrity: sha512-CQbKl57kdEv+KDLquhC+gE3pXt74LEAzm+tzywcA0/aHZuub8wTErbjAoNI57rPUWRYRNC5WUnNl8eGJNbDdwg==} @@ -8278,7 +8279,6 @@ packages: emoji-regex: 8.0.0 is-fullwidth-code-point: 3.0.0 strip-ansi: 6.0.1 - dev: true /string-width@5.1.2: resolution: {integrity: sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==} @@ -8362,7 +8362,6 @@ packages: engines: {node: '>=8'} dependencies: ansi-regex: 5.0.1 - dev: true /strip-ansi@7.1.0: resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==} @@ -8570,7 +8569,6 @@ packages: engines: {node: '>=0.6.0'} dependencies: os-tmpdir: 1.0.2 - dev: true /to-fast-properties@2.0.0: resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==} @@ -8626,7 +8624,6 @@ packages: /tslib@2.6.2: resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==} - dev: true /tuf-js@2.1.0: resolution: {integrity: sha512-eD7YPPjVlMzdggrOeE8zwoegUaG/rt6Bt3jwoQPunRiNVzgcCE009UDFJKJjG+Gk9wFu6W/Vi+P5d/5QpdD9jA==} @@ -8669,7 +8666,6 @@ packages: /type-fest@0.21.3: resolution: {integrity: sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==} engines: {node: '>=10'} - dev: true /type-fest@0.6.0: resolution: {integrity: sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==} @@ -9063,7 +9059,6 @@ packages: resolution: {integrity: sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==} dependencies: defaults: 1.0.4 - dev: true /web-streams-polyfill@3.2.1: resolution: {integrity: sha512-e0MO3wdXWKrLbL0DgGnUV7WHVuw9OUvL4hjgnPkIeEvESk74gAITi5G606JtZPp39cd8HA9VQzCIvA49LpPN5Q==} @@ -9333,7 +9328,6 @@ packages: ansi-styles: 4.3.0 string-width: 4.2.3 strip-ansi: 6.0.1 - dev: true /wrap-ansi@7.0.0: resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 3f4a902da4..14e351892a 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -1,3 +1,4 @@ packages: + - create/ - plugins/* - themes/* diff --git a/tsconfig.build.json b/tsconfig.build.json index 9ee2ff7c73..9f2c7bccd0 100644 --- a/tsconfig.build.json +++ b/tsconfig.build.json @@ -4,6 +4,7 @@ "composite": true }, "references": [ + { "path": "./create/tsconfig.build.json" }, { "path": "./plugins/plugin-active-header-links/tsconfig.build.json" }, diff --git a/tsconfig.json b/tsconfig.json index 4f1ccc692d..11213cc04a 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -16,6 +16,7 @@ }, "include": [ "**/.vuepress/**/*", + "create/**/*", "plugins/**/*", "themes/**/*", "vitest.config.ts" From bff464a7c5be758601c94773de54e0223f4f7ae0 Mon Sep 17 00:00:00 2001 From: "Mr.Hope" Date: Sun, 31 Dec 2023 03:39:06 +0800 Subject: [PATCH 2/5] chore: update create location --- pnpm-lock.yaml | 32 +++++++++---------- pnpm-workspace.yaml | 2 +- .../create-vuepress}/package.json | 0 .../create-vuepress}/src/action.ts | 0 .../create-vuepress}/src/config/index.ts | 0 .../src/flow/createPackageJson.ts | 0 .../src/flow/generateTemplate.ts | 0 .../create-vuepress}/src/flow/index.ts | 0 .../create-vuepress}/src/i18n/en.ts | 0 .../create-vuepress}/src/i18n/index.ts | 0 .../create-vuepress}/src/i18n/typings.ts | 0 .../create-vuepress}/src/i18n/zh.ts | 0 .../create-vuepress}/src/index.ts | 0 .../create-vuepress}/src/utils/file.ts | 0 .../src/utils/getPackageManager.ts | 0 .../create-vuepress}/src/utils/getRegistry.ts | 0 .../create-vuepress}/src/utils/index.ts | 0 .../src/utils/normalizeThemeName.ts | 0 .../create-vuepress}/src/utils/version.ts | 0 .../template/blog/.vuepress/blog-plugin.js | 0 .../template/blog/.vuepress/client.js | 0 .../blog/.vuepress/components/ArticleList.vue | 0 .../template/blog/.vuepress/config.js | 0 .../blog/.vuepress/layouts/Article.vue | 0 .../blog/.vuepress/layouts/Category.vue | 0 .../template/blog/.vuepress/layouts/Tag.vue | 0 .../blog/.vuepress/layouts/Timeline.vue | 0 .../create-vuepress}/template/blog/README.md | 0 .../template/blog/get-started.md | 0 .../template/blog/posts/archive1.md | 0 .../template/blog/posts/archive2.md | 0 .../template/blog/posts/article1.md | 0 .../template/blog/posts/article10.md | 0 .../template/blog/posts/article11.md | 0 .../template/blog/posts/article12.md | 0 .../template/blog/posts/article2.md | 0 .../template/blog/posts/article3.md | 0 .../template/blog/posts/article4.md | 0 .../template/blog/posts/article5.md | 0 .../template/blog/posts/article6.md | 0 .../template/blog/posts/article7.md | 0 .../template/blog/posts/article8.md | 0 .../template/blog/posts/article9.md | 0 .../template/blog/posts/sticky.md | 0 .../template/blog/posts/sticky2.md | 0 .../template/docs/.vuepress/config.js | 0 .../create-vuepress}/template/docs/README.md | 0 .../template/docs/get-started.md | 0 .../create-vuepress}/tsconfig.build.json | 2 +- tsconfig.build.json | 4 +-- tsconfig.json | 2 +- 51 files changed, 21 insertions(+), 21 deletions(-) rename {create => tools/create-vuepress}/package.json (100%) rename {create => tools/create-vuepress}/src/action.ts (100%) rename {create => tools/create-vuepress}/src/config/index.ts (100%) rename {create => tools/create-vuepress}/src/flow/createPackageJson.ts (100%) rename {create => tools/create-vuepress}/src/flow/generateTemplate.ts (100%) rename {create => tools/create-vuepress}/src/flow/index.ts (100%) rename {create => tools/create-vuepress}/src/i18n/en.ts (100%) rename {create => tools/create-vuepress}/src/i18n/index.ts (100%) rename {create => tools/create-vuepress}/src/i18n/typings.ts (100%) rename {create => tools/create-vuepress}/src/i18n/zh.ts (100%) rename {create => tools/create-vuepress}/src/index.ts (100%) rename {create => tools/create-vuepress}/src/utils/file.ts (100%) rename {create => tools/create-vuepress}/src/utils/getPackageManager.ts (100%) rename {create => tools/create-vuepress}/src/utils/getRegistry.ts (100%) rename {create => tools/create-vuepress}/src/utils/index.ts (100%) rename {create => tools/create-vuepress}/src/utils/normalizeThemeName.ts (100%) rename {create => tools/create-vuepress}/src/utils/version.ts (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/blog-plugin.js (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/client.js (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/components/ArticleList.vue (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/config.js (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/layouts/Article.vue (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/layouts/Category.vue (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/layouts/Tag.vue (100%) rename {create => tools/create-vuepress}/template/blog/.vuepress/layouts/Timeline.vue (100%) rename {create => tools/create-vuepress}/template/blog/README.md (100%) rename {create => tools/create-vuepress}/template/blog/get-started.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/archive1.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/archive2.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article1.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article10.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article11.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article12.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article2.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article3.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article4.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article5.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article6.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article7.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article8.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/article9.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/sticky.md (100%) rename {create => tools/create-vuepress}/template/blog/posts/sticky2.md (100%) rename {create => tools/create-vuepress}/template/docs/.vuepress/config.js (100%) rename {create => tools/create-vuepress}/template/docs/README.md (100%) rename {create => tools/create-vuepress}/template/docs/get-started.md (100%) rename {create => tools/create-vuepress}/tsconfig.build.json (74%) diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 4c66cf403e..fabc08ecdc 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -72,22 +72,6 @@ importers: specifier: ^1.1.0 version: 1.1.0(@types/node@20.10.5) - create: - dependencies: - cac: - specifier: ^6.7.14 - version: 6.7.14 - execa: - specifier: ^8.0.1 - version: 8.0.1 - inquirer: - specifier: ^9.2.12 - version: 9.2.12 - devDependencies: - '@types/inquirer': - specifier: 9.0.7 - version: 9.0.7 - plugins/plugin-active-header-links: dependencies: '@vuepress/client': @@ -482,6 +466,22 @@ importers: specifier: ^4.2.5 version: 4.2.5(vue@3.4.0) + tools/create-vuepress: + dependencies: + cac: + specifier: ^6.7.14 + version: 6.7.14 + execa: + specifier: ^8.0.1 + version: 8.0.1 + inquirer: + specifier: ^9.2.12 + version: 9.2.12 + devDependencies: + '@types/inquirer': + specifier: 9.0.7 + version: 9.0.7 + packages: /@aashutoshrathi/word-wrap@1.2.6: diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 14e351892a..90742d502d 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -1,4 +1,4 @@ packages: - - create/ - plugins/* - themes/* + - tools/* diff --git a/create/package.json b/tools/create-vuepress/package.json similarity index 100% rename from create/package.json rename to tools/create-vuepress/package.json diff --git a/create/src/action.ts b/tools/create-vuepress/src/action.ts similarity index 100% rename from create/src/action.ts rename to tools/create-vuepress/src/action.ts diff --git a/create/src/config/index.ts b/tools/create-vuepress/src/config/index.ts similarity index 100% rename from create/src/config/index.ts rename to tools/create-vuepress/src/config/index.ts diff --git a/create/src/flow/createPackageJson.ts b/tools/create-vuepress/src/flow/createPackageJson.ts similarity index 100% rename from create/src/flow/createPackageJson.ts rename to tools/create-vuepress/src/flow/createPackageJson.ts diff --git a/create/src/flow/generateTemplate.ts b/tools/create-vuepress/src/flow/generateTemplate.ts similarity index 100% rename from create/src/flow/generateTemplate.ts rename to tools/create-vuepress/src/flow/generateTemplate.ts diff --git a/create/src/flow/index.ts b/tools/create-vuepress/src/flow/index.ts similarity index 100% rename from create/src/flow/index.ts rename to tools/create-vuepress/src/flow/index.ts diff --git a/create/src/i18n/en.ts b/tools/create-vuepress/src/i18n/en.ts similarity index 100% rename from create/src/i18n/en.ts rename to tools/create-vuepress/src/i18n/en.ts diff --git a/create/src/i18n/index.ts b/tools/create-vuepress/src/i18n/index.ts similarity index 100% rename from create/src/i18n/index.ts rename to tools/create-vuepress/src/i18n/index.ts diff --git a/create/src/i18n/typings.ts b/tools/create-vuepress/src/i18n/typings.ts similarity index 100% rename from create/src/i18n/typings.ts rename to tools/create-vuepress/src/i18n/typings.ts diff --git a/create/src/i18n/zh.ts b/tools/create-vuepress/src/i18n/zh.ts similarity index 100% rename from create/src/i18n/zh.ts rename to tools/create-vuepress/src/i18n/zh.ts diff --git a/create/src/index.ts b/tools/create-vuepress/src/index.ts similarity index 100% rename from create/src/index.ts rename to tools/create-vuepress/src/index.ts diff --git a/create/src/utils/file.ts b/tools/create-vuepress/src/utils/file.ts similarity index 100% rename from create/src/utils/file.ts rename to tools/create-vuepress/src/utils/file.ts diff --git a/create/src/utils/getPackageManager.ts b/tools/create-vuepress/src/utils/getPackageManager.ts similarity index 100% rename from create/src/utils/getPackageManager.ts rename to tools/create-vuepress/src/utils/getPackageManager.ts diff --git a/create/src/utils/getRegistry.ts b/tools/create-vuepress/src/utils/getRegistry.ts similarity index 100% rename from create/src/utils/getRegistry.ts rename to tools/create-vuepress/src/utils/getRegistry.ts diff --git a/create/src/utils/index.ts b/tools/create-vuepress/src/utils/index.ts similarity index 100% rename from create/src/utils/index.ts rename to tools/create-vuepress/src/utils/index.ts diff --git a/create/src/utils/normalizeThemeName.ts b/tools/create-vuepress/src/utils/normalizeThemeName.ts similarity index 100% rename from create/src/utils/normalizeThemeName.ts rename to tools/create-vuepress/src/utils/normalizeThemeName.ts diff --git a/create/src/utils/version.ts b/tools/create-vuepress/src/utils/version.ts similarity index 100% rename from create/src/utils/version.ts rename to tools/create-vuepress/src/utils/version.ts diff --git a/create/template/blog/.vuepress/blog-plugin.js b/tools/create-vuepress/template/blog/.vuepress/blog-plugin.js similarity index 100% rename from create/template/blog/.vuepress/blog-plugin.js rename to tools/create-vuepress/template/blog/.vuepress/blog-plugin.js diff --git a/create/template/blog/.vuepress/client.js b/tools/create-vuepress/template/blog/.vuepress/client.js similarity index 100% rename from create/template/blog/.vuepress/client.js rename to tools/create-vuepress/template/blog/.vuepress/client.js diff --git a/create/template/blog/.vuepress/components/ArticleList.vue b/tools/create-vuepress/template/blog/.vuepress/components/ArticleList.vue similarity index 100% rename from create/template/blog/.vuepress/components/ArticleList.vue rename to tools/create-vuepress/template/blog/.vuepress/components/ArticleList.vue diff --git a/create/template/blog/.vuepress/config.js b/tools/create-vuepress/template/blog/.vuepress/config.js similarity index 100% rename from create/template/blog/.vuepress/config.js rename to tools/create-vuepress/template/blog/.vuepress/config.js diff --git a/create/template/blog/.vuepress/layouts/Article.vue b/tools/create-vuepress/template/blog/.vuepress/layouts/Article.vue similarity index 100% rename from create/template/blog/.vuepress/layouts/Article.vue rename to tools/create-vuepress/template/blog/.vuepress/layouts/Article.vue diff --git a/create/template/blog/.vuepress/layouts/Category.vue b/tools/create-vuepress/template/blog/.vuepress/layouts/Category.vue similarity index 100% rename from create/template/blog/.vuepress/layouts/Category.vue rename to tools/create-vuepress/template/blog/.vuepress/layouts/Category.vue diff --git a/create/template/blog/.vuepress/layouts/Tag.vue b/tools/create-vuepress/template/blog/.vuepress/layouts/Tag.vue similarity index 100% rename from create/template/blog/.vuepress/layouts/Tag.vue rename to tools/create-vuepress/template/blog/.vuepress/layouts/Tag.vue diff --git a/create/template/blog/.vuepress/layouts/Timeline.vue b/tools/create-vuepress/template/blog/.vuepress/layouts/Timeline.vue similarity index 100% rename from create/template/blog/.vuepress/layouts/Timeline.vue rename to tools/create-vuepress/template/blog/.vuepress/layouts/Timeline.vue diff --git a/create/template/blog/README.md b/tools/create-vuepress/template/blog/README.md similarity index 100% rename from create/template/blog/README.md rename to tools/create-vuepress/template/blog/README.md diff --git a/create/template/blog/get-started.md b/tools/create-vuepress/template/blog/get-started.md similarity index 100% rename from create/template/blog/get-started.md rename to tools/create-vuepress/template/blog/get-started.md diff --git a/create/template/blog/posts/archive1.md b/tools/create-vuepress/template/blog/posts/archive1.md similarity index 100% rename from create/template/blog/posts/archive1.md rename to tools/create-vuepress/template/blog/posts/archive1.md diff --git a/create/template/blog/posts/archive2.md b/tools/create-vuepress/template/blog/posts/archive2.md similarity index 100% rename from create/template/blog/posts/archive2.md rename to tools/create-vuepress/template/blog/posts/archive2.md diff --git a/create/template/blog/posts/article1.md b/tools/create-vuepress/template/blog/posts/article1.md similarity index 100% rename from create/template/blog/posts/article1.md rename to tools/create-vuepress/template/blog/posts/article1.md diff --git a/create/template/blog/posts/article10.md b/tools/create-vuepress/template/blog/posts/article10.md similarity index 100% rename from create/template/blog/posts/article10.md rename to tools/create-vuepress/template/blog/posts/article10.md diff --git a/create/template/blog/posts/article11.md b/tools/create-vuepress/template/blog/posts/article11.md similarity index 100% rename from create/template/blog/posts/article11.md rename to tools/create-vuepress/template/blog/posts/article11.md diff --git a/create/template/blog/posts/article12.md b/tools/create-vuepress/template/blog/posts/article12.md similarity index 100% rename from create/template/blog/posts/article12.md rename to tools/create-vuepress/template/blog/posts/article12.md diff --git a/create/template/blog/posts/article2.md b/tools/create-vuepress/template/blog/posts/article2.md similarity index 100% rename from create/template/blog/posts/article2.md rename to tools/create-vuepress/template/blog/posts/article2.md diff --git a/create/template/blog/posts/article3.md b/tools/create-vuepress/template/blog/posts/article3.md similarity index 100% rename from create/template/blog/posts/article3.md rename to tools/create-vuepress/template/blog/posts/article3.md diff --git a/create/template/blog/posts/article4.md b/tools/create-vuepress/template/blog/posts/article4.md similarity index 100% rename from create/template/blog/posts/article4.md rename to tools/create-vuepress/template/blog/posts/article4.md diff --git a/create/template/blog/posts/article5.md b/tools/create-vuepress/template/blog/posts/article5.md similarity index 100% rename from create/template/blog/posts/article5.md rename to tools/create-vuepress/template/blog/posts/article5.md diff --git a/create/template/blog/posts/article6.md b/tools/create-vuepress/template/blog/posts/article6.md similarity index 100% rename from create/template/blog/posts/article6.md rename to tools/create-vuepress/template/blog/posts/article6.md diff --git a/create/template/blog/posts/article7.md b/tools/create-vuepress/template/blog/posts/article7.md similarity index 100% rename from create/template/blog/posts/article7.md rename to tools/create-vuepress/template/blog/posts/article7.md diff --git a/create/template/blog/posts/article8.md b/tools/create-vuepress/template/blog/posts/article8.md similarity index 100% rename from create/template/blog/posts/article8.md rename to tools/create-vuepress/template/blog/posts/article8.md diff --git a/create/template/blog/posts/article9.md b/tools/create-vuepress/template/blog/posts/article9.md similarity index 100% rename from create/template/blog/posts/article9.md rename to tools/create-vuepress/template/blog/posts/article9.md diff --git a/create/template/blog/posts/sticky.md b/tools/create-vuepress/template/blog/posts/sticky.md similarity index 100% rename from create/template/blog/posts/sticky.md rename to tools/create-vuepress/template/blog/posts/sticky.md diff --git a/create/template/blog/posts/sticky2.md b/tools/create-vuepress/template/blog/posts/sticky2.md similarity index 100% rename from create/template/blog/posts/sticky2.md rename to tools/create-vuepress/template/blog/posts/sticky2.md diff --git a/create/template/docs/.vuepress/config.js b/tools/create-vuepress/template/docs/.vuepress/config.js similarity index 100% rename from create/template/docs/.vuepress/config.js rename to tools/create-vuepress/template/docs/.vuepress/config.js diff --git a/create/template/docs/README.md b/tools/create-vuepress/template/docs/README.md similarity index 100% rename from create/template/docs/README.md rename to tools/create-vuepress/template/docs/README.md diff --git a/create/template/docs/get-started.md b/tools/create-vuepress/template/docs/get-started.md similarity index 100% rename from create/template/docs/get-started.md rename to tools/create-vuepress/template/docs/get-started.md diff --git a/create/tsconfig.build.json b/tools/create-vuepress/tsconfig.build.json similarity index 74% rename from create/tsconfig.build.json rename to tools/create-vuepress/tsconfig.build.json index c00ebcd6b4..4f60f73883 100644 --- a/create/tsconfig.build.json +++ b/tools/create-vuepress/tsconfig.build.json @@ -1,5 +1,5 @@ { - "extends": "../tsconfig.build.json", + "extends": "../../tsconfig.build.json", "compilerOptions": { "rootDir": "./src", "outDir": "./lib", diff --git a/tsconfig.build.json b/tsconfig.build.json index 9f2c7bccd0..91be61435a 100644 --- a/tsconfig.build.json +++ b/tsconfig.build.json @@ -4,7 +4,6 @@ "composite": true }, "references": [ - { "path": "./create/tsconfig.build.json" }, { "path": "./plugins/plugin-active-header-links/tsconfig.build.json" }, @@ -35,7 +34,8 @@ { "path": "./plugins/plugin-shiki/tsconfig.build.json" }, { "path": "./plugins/plugin-theme-data/tsconfig.build.json" }, { "path": "./plugins/plugin-toc/tsconfig.build.json" }, - { "path": "./themes/theme-default/tsconfig.build.json" } + { "path": "./themes/theme-default/tsconfig.build.json" }, + { "path": "./tools/create-vuepress/tsconfig.build.json" } ], "files": [] } diff --git a/tsconfig.json b/tsconfig.json index 11213cc04a..6bc7d836dd 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -16,9 +16,9 @@ }, "include": [ "**/.vuepress/**/*", - "create/**/*", "plugins/**/*", "themes/**/*", + "tools/**/*", "vitest.config.ts" ], "exclude": ["node_modules", ".temp", "lib", "dist"] From 61dd31dfd2339c65f94d492acfb74db773cd3299 Mon Sep 17 00:00:00 2001 From: "Mr.Hope" Date: Wed, 24 Jan 2024 12:59:59 +0800 Subject: [PATCH 3/5] fix: fix create template --- tools/create-vuepress/src/action.ts | 48 ++++++++++++++++--- .../src/flow/createPackageJson.ts | 22 ++++++--- .../src/flow/generateTemplate.ts | 45 +++++++++++++---- tools/create-vuepress/src/i18n/en.ts | 2 + tools/create-vuepress/src/i18n/typings.ts | 2 + tools/create-vuepress/src/i18n/zh.ts | 2 + tools/create-vuepress/src/utils/file.ts | 10 ++-- .../template/blog/.vuepress/blog-plugin.js | 42 ++++++++-------- .../template/blog/.vuepress/config.js | 2 +- 9 files changed, 125 insertions(+), 50 deletions(-) diff --git a/tools/create-vuepress/src/action.ts b/tools/create-vuepress/src/action.ts index c896c72974..892b707500 100644 --- a/tools/create-vuepress/src/action.ts +++ b/tools/create-vuepress/src/action.ts @@ -14,13 +14,18 @@ import { } from './utils/index.js' interface CreateOptions { + bundler?: 'vite' | 'webpack' | null preset?: 'docs' | 'blog' | null theme?: string } export const mainAction = async ( targetDir: string, - { preset = null, theme = '@vuepress/theme-default' }: CreateOptions, + { + bundler = null, + preset = null, + theme = '@vuepress/theme-default', + }: CreateOptions, ): Promise => { // get language const { lang, locale } = await getLanguage() @@ -42,6 +47,10 @@ export const mainAction = async ( if (theme !== '@vuepress/theme-default') console.warn(locale.error.theme) + // check bundler + if (bundler && !['vite', 'webpack'].includes(bundler)) + return console.log(locale.error.bundler) + // check presets if (preset && !['docs', 'blog'].includes(preset)) return console.log(locale.error.preset) @@ -58,10 +67,20 @@ export const mainAction = async ( ensureDirExistSync(targetDirPath) - /* - * Generate template - */ + // complete bundler + if (!bundler) + bundler = ( + await inquirer.prompt<{ bundler: 'vite' | 'webpack' }>([ + { + name: 'bundler', + type: 'list', + message: locale.question.bundler, + choices: ['vite', 'webpack'], + }, + ]) + ).bundler + // complete preset if (!preset) preset = ( await inquirer.prompt<{ preset: 'blog' | 'docs' }>([ @@ -74,8 +93,25 @@ export const mainAction = async ( ]) ).preset - await createPackageJson(targetDir, packageManager, locale, preset) - await generateTemplate(targetDir, packageManager, lang, locale, preset) + /* + * Generate template + */ + + await createPackageJson({ + targetDir, + packageManager, + locale, + preset, + bundler, + }) + await generateTemplate({ + targetDirPath, + packageManager, + lang, + locale, + preset, + bundler, + }) /* * Install deps diff --git a/tools/create-vuepress/src/flow/createPackageJson.ts b/tools/create-vuepress/src/flow/createPackageJson.ts index 79e3334413..ae80b44bf4 100644 --- a/tools/create-vuepress/src/flow/createPackageJson.ts +++ b/tools/create-vuepress/src/flow/createPackageJson.ts @@ -9,6 +9,14 @@ const PACKAGE_NAME_REG = const VERSION_REG = /^[0-9]+\.[0-9]+\.(?:[0-9]+|[0-9]+-[a-z]+\.[0-9])$/u +interface CreatePackageJsonOptions { + targetDir: string + packageManager: PackageManager + locale: CreateLocaleOptions + preset: 'blog' | 'docs' + bundler: 'vite' | 'webpack' +} + interface PackageJsonAnswer { name: string version: string @@ -19,16 +27,18 @@ interface PackageJsonAnswer { /** * generate package.json */ -export const createPackageJson = async ( - targetDir: string, - packageManager: PackageManager, - locale: CreateLocaleOptions, - preset: 'blog' | 'docs', -): Promise => { +export const createPackageJson = async ({ + targetDir, + packageManager, + locale, + preset, + bundler, +}: CreatePackageJsonOptions): Promise => { const packageJsonPath = join(targetDir, 'package.json') // TODO: Update it const devDependencies = { '@vuepress/client': '^2.0.0-rc.0', + [`@vuepress/bundler-${bundler}`]: '^2.0.0-rc.0', '@vuepress/theme-default': '^2.0.0-rc.0', 'vue': '^3.4.0', 'vuepress': '^2.0.0-rc.0', diff --git a/tools/create-vuepress/src/flow/generateTemplate.ts b/tools/create-vuepress/src/flow/generateTemplate.ts index c0fd37c483..e2e5e19194 100644 --- a/tools/create-vuepress/src/flow/generateTemplate.ts +++ b/tools/create-vuepress/src/flow/generateTemplate.ts @@ -1,4 +1,4 @@ -import { writeFileSync } from 'node:fs' +import { readFileSync, writeFileSync } from 'node:fs' import { createRequire } from 'node:module' import { dirname, join } from 'node:path' import inquirer from 'inquirer' @@ -97,13 +97,23 @@ ${ folder: src/.vuepress/dist ` -export const generateTemplate = async ( - targetDir: string, - packageManager: PackageManager, - lang: Lang, - locale: CreateLocaleOptions, - preset: 'blog' | 'docs', -): Promise => { +interface GenerateTemplateOptions { + targetDirPath: string + lang: Lang + packageManager: PackageManager + locale: CreateLocaleOptions + preset: 'blog' | 'docs' + bundler: 'vite' | 'webpack' +} + +export const generateTemplate = async ({ + targetDirPath, + packageManager, + lang, + locale, + preset, + bundler, +}: GenerateTemplateOptions): Promise => { const { workflow } = await inquirer.prompt<{ workflow: boolean }>([ @@ -118,10 +128,25 @@ export const generateTemplate = async ( console.log(locale.flow.generateTemplate) // copy template - copy(join(templateFolder, preset), join(targetDir, 'src')) + copy(join(templateFolder, preset), join(targetDirPath, 'src')) + + const configFilePath = join(targetDirPath, 'src/.vuepress/config.js') + + const content = readFileSync(configFilePath, { encoding: 'utf-8' }) + + writeFileSync( + configFilePath, + content + .replace( + /\n\nexport default defineUserConfig\(\{/, + `\nimport { ${bundler}Bundler } from '@vuepress/bundler-${bundler}'\n\nexport default defineUserConfig({`, + ) + .replace(/\}\)\n$/, `\n bundler: ${bundler}Bundler(),\n})\n`), + { encoding: 'utf-8' }, + ) if (workflow) { - const workflowDir = join(targetDir, '.github/workflows') + const workflowDir = join(targetDirPath, '.github/workflows') ensureDirExistSync(workflowDir) diff --git a/tools/create-vuepress/src/i18n/en.ts b/tools/create-vuepress/src/i18n/en.ts index 801a71035a..6e8202ec96 100644 --- a/tools/create-vuepress/src/i18n/en.ts +++ b/tools/create-vuepress/src/i18n/en.ts @@ -14,6 +14,7 @@ export const en: CreateLocaleOptions = { question: { i18n: 'Does the project need multiple languages?', workflow: 'Do you need a GitHub workflow to deploy docs on GitHub pages?', + bundler: 'Which bundler do you want to use?', preset: 'What type of project do you want to create?', packageManager: 'Choose package manager', devServer: 'Would you like to preview template now?', @@ -34,6 +35,7 @@ export const en: CreateLocaleOptions = { error: { name: 'package name should only contain lowercase characters, numbers and dash', version: "This version is not a valid one. Version should be like 'x.x.x'", + bundler: 'bundler (--bundler) only support "vite" or "webpack"', preset: 'preset (--preset) only support "doc" or "blog"', theme: 'Current theme is not supported yet, using @vuepress/theme-default instead.', diff --git a/tools/create-vuepress/src/i18n/typings.ts b/tools/create-vuepress/src/i18n/typings.ts index b494c33bc6..45579f1263 100644 --- a/tools/create-vuepress/src/i18n/typings.ts +++ b/tools/create-vuepress/src/i18n/typings.ts @@ -19,6 +19,7 @@ export interface CreateLocaleOptions { description: string license: string workflow: string + bundler: string preset: string devServer: string } @@ -32,6 +33,7 @@ export interface CreateLocaleOptions { error: { name: string version: string + bundler: string preset: string theme: string dirMissing: (packageManager: PackageManager) => string diff --git a/tools/create-vuepress/src/i18n/zh.ts b/tools/create-vuepress/src/i18n/zh.ts index 0cd5ab3d22..12c6addc5e 100644 --- a/tools/create-vuepress/src/i18n/zh.ts +++ b/tools/create-vuepress/src/i18n/zh.ts @@ -15,6 +15,7 @@ export const zh: CreateLocaleOptions = { packageManager: '选择包管理器', i18n: '项目需要用到多语言么?', workflow: '是否需要一个自动部署文档到 GitHub Pages 的工作流?', + bundler: '你想要使用哪个打包器?', preset: '你想要创建什么类型的项目?', devServer: '是否想要现在启动 Demo 查看?', name: '设置应用名称', @@ -34,6 +35,7 @@ export const zh: CreateLocaleOptions = { error: { name: '应用名称应只包含小写字母、数字和连接线 (-)', version: "此版本无效,版本号应为 'x.x.x'", + bundler: '打包器 (--bundler) 仅支持 vite 或 webpack', preset: '预设 (--preset) 仅支持 doc 或 blog', theme: '当前主题暂不支持,将使用 @vuepress/theme-default 代替', dirMissing: (packageManager: PackageManager): string => diff --git a/tools/create-vuepress/src/utils/file.ts b/tools/create-vuepress/src/utils/file.ts index 669faff096..f42fe0f969 100644 --- a/tools/create-vuepress/src/utils/file.ts +++ b/tools/create-vuepress/src/utils/file.ts @@ -1,9 +1,9 @@ import { - createReadStream, - createWriteStream, mkdirSync, readdirSync, + readFileSync, statSync, + writeFileSync, } from 'node:fs' import { dirname } from 'node:path' @@ -23,11 +23,7 @@ export const copyFile = (srcFile: string, targetFile: string): void => { const targetDir = dirname(targetFile) ensureDirExistSync(targetDir) - - const rs = createReadStream(srcFile) // create read stream - const ws = createWriteStream(targetFile) // create write stream - - rs.pipe(ws) + writeFileSync(targetFile, readFileSync(srcFile)) } export const copyDir = (srcDir: string, targetDir: string): void => { diff --git a/tools/create-vuepress/template/blog/.vuepress/blog-plugin.js b/tools/create-vuepress/template/blog/.vuepress/blog-plugin.js index f069e2e569..dccdb0f112 100644 --- a/tools/create-vuepress/template/blog/.vuepress/blog-plugin.js +++ b/tools/create-vuepress/template/blog/.vuepress/blog-plugin.js @@ -13,28 +13,30 @@ const generateCategory = async (app, name) => { const value = page.frontmatter[name] await (Array.isArray(value) ? value : [value]).map(async (item) => { - if (item && !map[item]) { - const itemPath = `/${name}/${slugify(item)}/` + if (item) { + if (!map[item]) { + const itemPath = `/${name}/${slugify(item)}/` - map[item] = { - path: itemPath, - keys: [], + map[item] = { + path: itemPath, + keys: [], + } + + app.pages.push( + await createPage(app, { + path: itemPath, + frontmatter: { + title: `${name} > ${item}`, + key: item, + layout: name[0].toUpperCase() + name.slice(1), + sidebar: false, + }, + }), + ) } - app.pages.push( - await createPage(app, { - path: itemPath, - frontmatter: { - title: `${name} > ${item}`, - key: item, - layout: name, - sidebar: false, - }, - }), - ) + map[item].keys.push(page.key) } - - map[item].keys.push(page.key) }) }) @@ -43,7 +45,7 @@ const generateCategory = async (app, name) => { path: `/${name}/`, frontmatter: { title: name, - layout: name, + layout: name[0].toUpperCase() + name.slice(1), sidebar: false, }, }), @@ -67,7 +69,7 @@ const generateType = async ( path: `/${name}/`, frontmatter: { title: name, - layout: name, + layout: name[0].toUpperCase() + name.slice(1), sidebar: false, }, }), diff --git a/tools/create-vuepress/template/blog/.vuepress/config.js b/tools/create-vuepress/template/blog/.vuepress/config.js index f8c00b362f..617e741e74 100644 --- a/tools/create-vuepress/template/blog/.vuepress/config.js +++ b/tools/create-vuepress/template/blog/.vuepress/config.js @@ -1,6 +1,6 @@ import { defaultTheme } from '@vuepress/theme-default' import { defineUserConfig } from 'vuepress' -import { simpleBlogPlugin } from './blog-plugin' +import { simpleBlogPlugin } from './blog-plugin.js' export default defineUserConfig({ lang: 'en-US', From 1db7729133fc621aecdcec299b11acbddd1c0fd6 Mon Sep 17 00:00:00 2001 From: "Mr.Hope" Date: Fri, 26 Jan 2024 13:16:47 +0800 Subject: [PATCH 4/5] build: update commitlint --- .commitlintrc.cjs | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/.commitlintrc.cjs b/.commitlintrc.cjs index 66130dc183..2ec0c0f2c9 100644 --- a/.commitlintrc.cjs +++ b/.commitlintrc.cjs @@ -8,11 +8,16 @@ const getSubDirectories = (dir) => const pluginPackages = getSubDirectories(path.resolve(__dirname, 'plugins')) const themePackages = getSubDirectories(path.resolve(__dirname, 'themes')) +const toolsPackages = getSubDirectories(path.resolve(__dirname, 'tools')) module.exports = { extends: ['@commitlint/config-conventional'], rules: { - 'scope-enum': [2, 'always', ['e2e', ...pluginPackages, ...themePackages]], + 'scope-enum': [ + 2, + 'always', + ['e2e', ...pluginPackages, ...themePackages, ...toolsPackages], + ], 'footer-max-line-length': [0], }, } From 59fb71ac8a97987c16790864fdfdd7e0f03f16b6 Mon Sep 17 00:00:00 2001 From: "Mr.Hope" Date: Fri, 26 Jan 2024 13:22:06 +0800 Subject: [PATCH 5/5] style: fix linter --- .eslintrc.cjs | 9 ++++++++- tools/create-vuepress/template/blog/.vuepress/config.js | 2 +- tools/create-vuepress/template/docs/.vuepress/config.js | 2 +- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/.eslintrc.cjs b/.eslintrc.cjs index e36154fb2a..cb61b75740 100644 --- a/.eslintrc.cjs +++ b/.eslintrc.cjs @@ -21,9 +21,16 @@ module.exports = { }, }, { - files: ['**/e2e/**/*.cy.ts', '**/e2e/cypress/**/*.ts'], + files: ['e2e/**/*.cy.ts', 'e2e/cypress/**/*.ts'], extends: 'plugin:cypress/recommended', }, + { + files: ['tools/create-helper/**/*.ts', 'tools/create-helper/**/*.vue'], + rules: { + 'import/no-extraneous-dependencies': 'off', + 'import/named': 'off', + }, + }, { files: ['**/tests/**/*.ts'], rules: { diff --git a/tools/create-vuepress/template/blog/.vuepress/config.js b/tools/create-vuepress/template/blog/.vuepress/config.js index 617e741e74..4d5a307198 100644 --- a/tools/create-vuepress/template/blog/.vuepress/config.js +++ b/tools/create-vuepress/template/blog/.vuepress/config.js @@ -1,5 +1,5 @@ import { defaultTheme } from '@vuepress/theme-default' -import { defineUserConfig } from 'vuepress' +import { defineUserConfig } from 'vuepress/cli' import { simpleBlogPlugin } from './blog-plugin.js' export default defineUserConfig({ diff --git a/tools/create-vuepress/template/docs/.vuepress/config.js b/tools/create-vuepress/template/docs/.vuepress/config.js index 5d3c5cbf93..3bf74af455 100644 --- a/tools/create-vuepress/template/docs/.vuepress/config.js +++ b/tools/create-vuepress/template/docs/.vuepress/config.js @@ -1,5 +1,5 @@ import { defaultTheme } from '@vuepress/theme-default' -import { defineUserConfig } from 'vuepress' +import { defineUserConfig } from 'vuepress/cli' export default defineUserConfig({ lang: 'en-US',