自定义Vue-CLI模板
实现的原理是 Vue CLI preset ,即在创建新项目时使用预定义的配置和要用到的插件,而这些预定义的内容支持放在 Git 上(包括 GitHub、GitLab 等),使用远程仓库中的 Preset 创建 Vue 项目时需要加入特殊的选项:
# GitHub
$ vue create --preset <username>/<repo> <vue_project_name>
# GitLab 私有服务器
$ vue create --preset direct:https://gitlab.xxx.xx/vue-preset.git --clone <vue_project_name>
# 本地
$ vue craete ./<project_name> <vue_project_name>
初始化 Preset 目录结构
创建目录
.
├─ template/
│ └─ ...
├─ generator.js
├─ preset.json
├─ prompts.js
添加预定义文件
preset.json 是使用 $ vue create 命令时自动生成的预定义选项的 JSON 文件,Windows位于C:\Users\电脑名称\ .vuerc ,MacOS 中位于 ~/.vuerc。文件的内容会显示选择的内容:
{
"useTaobaoRegistry": true,
"packageManager": "yarn"
}
之后创建项目就会采用改预定选项,不再进行提示,以下是本地示例:
{
"useConfigFiles": true,
"cssPreprocessor": "less",
"plugins": {
"@vue/cli-plugin-babel": {},
"@vue/cli-plugin-eslint": {
"config": "airbnb",
"lintOn": ["save", "commit"]
},
"@vue/cli-plugin-router": {},
"@vue/cli-plugin-vuex": {}
}
}
具体参考官网 Vue CLI preset
定义模板
本人项目模板
D:.
│ .editorconfig
│ .env
│ .env.dev
│ .env.dev213
│ .env.prd
│ .env.prd213
│ .eslintignore
│ .gitattributes
│ .gitignore
│ .npmrc
│ .prettierrc
│ babel.config.js
│ dev.js
│ Directory.txt
│ idea.config.js
│ LICENSE
│ package-lock.json
│ package.json
│ README.md
│ sentry.config.js
│ vue.config.js
│ webstorm.config.js
│ yarn
│ yarn.lock
│
├─ModifyScript
│ beifen.js
│ config.js
│
├─public
│ │ color.less
│ │ favicon.ico
│ │ goright.png
│ │ index.html
│ │ v2.js
│ │
│ ├─dev
│ │ favicon.ico
│ │
│ └─tinymce
│ │ emojis.js
│ │
│ ├─langs
│ │ zh_CN.js
│ │
│ └─skins
│ └─lightgray
│ content.min.css
│ skin.min.css
│
└─src
│ App.vue
│ defaultSettings.js
│ main.js
│ permission.js
│
├─api
│ ├─dbcp
│ │ offer.js
│ │
│ └─teamwork
│ index.js
│ information.js
│ workflow.js
│
├─components
│ │ ChartCard.vue
│ │ index.less
│ │ README.md
.......
需要注意的地方
-
如果模板中没有定义 Vue CLI 本身就会生成的文件,则默认采用原来的,如
view/目录下的 Home.vue 和 About.vue 等 -
以
.开头的模板文件需要将.改为_,以_开头的模板文件要定义成__,否则无法正确渲染 -
空文件夹不会被正确渲染
-
因为Vue-CLI 会使用EJS渲染,所以模板如果有EJS代码可能会报错,例如:
<link rel="icon" href="<%= VUE_APP_BASE_URL %>favicon.ico">运行会报
VUE_APP_BASE_URL找不到,所以需要直接将<%= VUE_APP_BASE_URL %>当成字符串渲染出来,就要改成:<link rel="icon" href="<%%= VUE_APP_BASE_URL %%>favicon.ico">
扩展依赖包
genarator.js 文件用来为项目添加其它依赖,比如 UI 框架、工具类库等等,渲染 template 模板的操作也需要在该文件内完成。该文件需要导出一个函数,包含三个参数:
- api:generator 实例,函数中可以操作该实例,比如扩展依赖、检查插件、查看版本等
- options:定制 Vue CLI 时与交互式命令行结合使用,用来接收答案参数
- rootOptions:预定义的所有内容,也就是 preset.json 中的所有内容,并且包含项目名称、src/main.js 中配置的说明等:
{
"useConfigFiles": true,
"cssPreprocessor": "less",
"plugins": {
"@vue/cli-plugin-babel": {},
"@vue/cli-plugin-eslint": {
"config": "airbnb",
"lintOn": ["save", "commit"]
},
"@vue/cli-plugin-router": {},
"@vue/cli-plugin-vuex": {}
}
}
添加依赖项
为项目添加脚本和依赖项需要使用 generator 实例的 extendPackage() 方法,内容和 package.json 无异,根据依赖的类型声明 NPM 包名和版本即可,创建项目时会自行安装声明的依赖项:
api.extendPackage({
"dependencies": {
"@antv/data-set": "^0.11.2",
"@jeecg/antd-online-beta220": "^1.0.1",
...
},
"devDependencies": {
"@babel/polyfill": "^7.2.5",
"@vue/cli-plugin-babel": "^3.3.0",
...
},
scripts: {
"pre": "yarn --registry https://registry.npm.taobao.org || cnpm install || npm install --registry https://registry.npm.taobao.org ",
"dev": "node dev.js && vue-cli-service serve --mode dev",
"build:prd": "cross-env VUE_APP_RELEASE= npm run gitHash && npm run build -- --mode prd && git rev-parse --short HEAD > ./dist/version",
"build:test": "cross-env VUE_APP_RELEASE= npm run gitHash && npm run build -- --mode test",
"build:beta": "cross-env VUE_APP_RELEASE= npm run gitHash && npm run build -- --mode prdBeta && git rev-parse --short HEAD > ./dist/version",
"build": "node --max_old_space_size=20000 node_modules/@vue/cli-service/bin/vue-cli-service.js build",
"gitHash": "cross-env-shell \"git rev-parse --short HEAD\"",
"lint": "vue-cli-service lint",
"build213": "cross-env VUE_APP_RELEASE= npm run gitHash && npm run build -- --mode prd213 && git rev-parse --short HEAD > ./dist/version"
}
})
渲染模板
使用 render() 方法来渲染 template 中定义的模板,该方法实际使用 EJS 进行渲染,可以传入一个相对路径的字符串,会将原本的目录直接替换。也可以传入 Hash 对象,文件对应文件来渲染(不能是文件夹),写多个 rander() 的话会依次执行:
api.render('./template');
api.render({
'./.eslintrc.js': './template/_eslintrc.js',
'./.gitignore': './template/_gitignore'
})
交互式命令行
是一个内建对话配置文件,进行安装时提示用户的操作流程
很多命令行操作都涉及对话的情境,比如 Git 操作、各种 CLI 操作,看起来比较 Geek,实现原理是 Node.js 的交互式命令行 Inquirer.js。要想自定义 Vue CLI 的对话内容需要用到 prompts.js 文件,该文件内应导出一个与 inquirer.prompt() 参数相同数据结构的数组,数组内每一个对象都作为一个命令行中的问题
module.exports = [
{
type: "confirm", // 问题类型
name: "sentry", // 存储答案的 key
message: "是否使用 sentry", // 问题的内容
default: false, // 未选择时的默认值
choices: [ // 可选项
{
name: '是', // 选项
value: true // 选项对应的值
},
{
name: '否', // 选项
value: false // 选项对应的值
}
]
},
{
type: "confirm", // 问题类型
name: "micro", // 存储答案的 key
message: "是否参与微前端", // 问题的内容
default: false, // 未选择时的默认值
choices: [ // 可选项
{
name: '是', // 选项
value: true // 选项对应的值
},
{
name: '否', // 选项
value: false // 选项对应的值
}
]
},
{
name: "app",
type: "input",
message: "请为你的app起个名字(xxxApp)",
when: (answers) => answers.micro,
},
]
完成对话后应该按照不同的答案执行不同的操作,上面 genarator.js 文件中的函数的 options 参数就起到作用了,可以在函数中打印 options,答案以 Key-value 的形式保存在一个对象内