原文地址在底部
这可能是vue-cli最全的解析了……
题言:
相信很多vue新手,都像我一样,只是知道可以用vue-cli直接生成一个vue项目的架构,并不明白,他究竟是怎么运行的,现在我们一起来研究一下。。。
一、安装vue-cli,相信你既然会用到vue-cli,自然node环境是OK的,直接命令行下安装
npm install -g vue-cli
二、使用vue-cli创建vue项目
用法: vue init

1template-name:2 . webpack3. webpack-simple// 一个简单webpack+vue-loader的模板,不包含其他功能。4. browserify// 一个全面的Browserify+vueify 的模板,功能包括热加载,linting,单元检测。5. browserify-simple// 一个简单Browserify+vueify的模板,不包含其他功能。6. pwa// 基于webpack模板的vue-cli的PWA模板7. simple// 一个最简单的单页应用模板

常用的就是webpack了,模板之间的不同,自己体验
示例:
vue init webpack my-project
执行指令后,会让用户输入几个基本的选项,如图所示
需要注意的是项目的名称不能大写,不然会报错。
Project name :项目名称 ,如果不需要更改直接回车就可以了。注意:这里不能使用大写。
Project description:项目描述,默认为A Vue.js project,直接回车,不用编写。
Author:作者,如果你有配置git,他会读取.ssh文件中的user。
Install vue-router? 是否安装vue的路由插件,Y代表安装,N无需安装,下面的命令也是一样的。
Use ESLint to lint your code? 是否用ESLint来限制你的代码错误和风格
setup unit tests with Karma + Mocha? 是否需要安装单元测试工具Karma+Mocha。
Setup e2e tests with Nightwatch?是否安装e2e来进行用户行为模拟测试。
Should we run npm install for you after the project has been created?(recommended)npm
询问你使用npm安装还是yarn安装包依赖,我这里选择的是npm,yarn更快更好,使用yarn之前确保你的电脑已经安装yarn。
根据提示,待模板加载完成之后,执行下面两条命令
cd my-project
npm run dev // dev代表下图框选的内容
出现如图,就是编译成功了,英文稍微好点,就能读懂
这时候,鼠标放到http://localhost:8080会提示用“Alt+点击”即可访问;
出现如图,就成功创建了项目;
三、文件目录结构
本文主要分析开发(dev)和构建(build)两个过程涉及到的文件,故下面文件结构仅列出相应的内容。

|-- build// 项目构建(webpack)相关代码| |-- build.js// 生产环境构建代码| |-- check-version.js// 检查node、npm等版本| |-- utils.js// 构建工具相关| |-- vue-loader.conf.js// webpack loader配置| |-- webpack.base.conf.js// webpack基础配置| |-- webpack.dev.conf.js// webpack开发环境配置,构建开发本地服务器| |-- webpack.prod.conf.js// webpack生产环境配置|-- config// 项目开发环境配置| |-- dev.env.js// 开发环境变量| |-- index.js// 项目一些配置变量| |-- prod.env.js// 生产环境变量| |-- test.env.js// 测试脚本的配置|-- src// 源码目录| |-- components// vue所有组件| |-- router// vue的路由管理| |-- App.vue// 页面入口文件| |-- main.js// 程序入口文件,加载各种公共组件|-- static// 静态文件,比如一些图片,json数据等|-- test// 测试文件| |-- e2e// e2e 测试| |-- unit// 单元测试|-- .babelrc// ES6语法编译配置|-- .editorconfig// 定义代码格式|-- .eslintignore// eslint检测代码忽略的文件(夹)|-- .eslintrc.js// 定义eslint的plugins,extends,rules|-- .gitignore// git上传需要忽略的文件格式|-- .postcsssrc// postcss配置文件|-- README.md// 项目说明,markdown文档|-- index.html// 访问的页面|-- package.json// 项目基本信息,包依赖信息等

如图所示:
下边是具体文件的具体分析
1. package.json文件
package.json文件是项目的配置文件,定义了项目的基本信息以及项目的相关包依赖,npm运行命令等
scripts里定义的是一些比较长的命令,用node去执行一段命令,比如
npm run dev
其实就是执行
webpack-dev-server --inline --progress --config build/webpack.dev.conf.js
这句话的意思是利用 webpack-dev-server 读取 webpack.dev.conf.js 信息并启动一个本地服务器。
2. dependencies VS devDependencies
简单的来说
dependencies 是运行时依赖(生产环境) npm install --save **(package name)
devDependencies 是开发时的依赖(开发环境) npm install --save-dev **(package name)
3. 基础配置文件 webpack.base.conf.js
基础的 webpack 配置文件主要根据模式定义了入口出口,以及处理 vue, babel等的各种模块,是最为基础的部分。其他模式的配置文件以此为基础通过 webpack-merge 合并。

1'use strict' 2const path = require('path') 3const utils = require('./utils') 4const config = require('../config') 5const vueLoaderConfig = require('./vue-loader.conf') 6 7// 获取绝对路径 8function resolve (dir) { 9returnpath.join(__dirname, '..', dir) 10} 11 12const createLintingRule = () => ({ 13test: /\.(js|vue)$/, 14loader: 'eslint-loader', 15enforce: 'pre', 16include: [resolve('src'), resolve('test')], 17 options: { 18formatter: require('eslint-friendly-formatter'), 19emitWarning: !config.dev.showEslintErrorsInOverlay 20 } 21}) 22 23module.exports = { 24// 基础上下文 25context: path.resolve(__dirname, '../'), 26// webpack的入口文件 27 entry: { 28app: './src/main.js' 29 }, 30// webpack的输出文件 31 output: { 32 path: config.build.assetsRoot, 33filename: '[name].js', 34publicPath: process.env.NODE_ENV === 'production' 35? config.build.assetsPublicPath 36 : config.dev.assetsPublicPath 37 }, 38/** 39 * 当webpack试图去加载模块的时候,它默认是查找以 .js 结尾的文件的, 40 * 它并不知道 .vue 结尾的文件是什么鬼玩意儿, 41 * 所以我们要在配置文件中告诉webpack, 42 * 遇到 .vue 结尾的也要去加载, 43 * 添加 resolve 配置项,如下: 44*/ 45 resolve: { 46extensions: ['.js', '.vue', '.json'], 47alias: {// 创建别名 48'vue$': 'vue/dist/vue.esm.js', 49'@': resolve('src'),// 如 '@/components/HelloWorld' 50 } 51 }, 52// 不同类型模块的处理规则 就是用不同的loader处理不同的文件 53 module: { 54 rules: [ 55...(config.dev.useEslint ? [createLintingRule()] : []), 56{// 对所有.vue文件使用vue-loader进行编译 57test: /\.vue$/, 58loader: 'vue-loader', 59 options: vueLoaderConfig 60 }, 61{// 对src和test文件夹下的.js文件使用babel-loader将es6+的代码转成es5 62test: /\.js$/, 63loader: 'babel-loader', 64include: [resolve('src'), resolve('test'), resolve('node_modules/webpack-dev-server/client')] 65 }, 66{// 对图片资源文件使用url-loader 67test: /\.(png|jpe?g|gif|svg)(\?.*)?$/, 68loader: 'url-loader', 69 options: { 70// 小于10K的图片转成base64编码的dataURL字符串写到代码中 71limit: 10000, 72// 其他的图片转移到静态资源文件夹 73name: utils.assetsPath('img/[name].[hash:7].[ext]') 74 } 75 }, 76{// 对多媒体资源文件使用url-loader 77test: /\.(mp4|webm|ogg|mp3|wav|flac|aac)(\?.*)?$/, 78loader: 'url-loader', 79 options: { 80// 小于10K的资源转成base64编码的dataURL字符串写到代码中 81limit: 10000, 82// 其他的资源转移到静态资源文件夹 83name: utils.assetsPath('media/[name].[hash:7].[ext]') 84 } 85 }, 86{// 对字体资源文件使用url-loader 87test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/, 88loader: 'url-loader', 89 options: { 90limit: 10000, 91name: utils.assetsPath('fonts/[name].[hash:7].[ext]')// hash:7 代表 7 位数的 hash 92 } 93 } 94 ] 95 }, 96 node: { 97// prevent webpack from injecting useless setImmediate polyfill because Vue 98// source contains it (although only uses it if it's native). 99setImmediate:false,100// prevent webpack from injecting mocks to Node native modules101// that does not make sense for the client102dgram: 'empty',103fs: 'empty',104net: 'empty',105tls: 'empty',106child_process: 'empty'107 }108}

4. 开发环境配置文件 webpack.dev.conf.js

1'use strict' 2const utils = require('./utils') 3const webpack = require('webpack') 4const config = require('../config')// 基本配置的参数 5const merge = require('webpack-merge')// webpack-merge是一个可以合并数组和对象的插件 6const path = require('path') 7const baseWebpackConfig = require('./webpack.base.conf')// webpack基本配置文件(开发和生产环境公用部分) 8const CopyWebpackPlugin = require('copy-webpack-plugin') 9// html-webpack-plugin用于将webpack编译打包后的产品文件注入到html模板中 10// 即在index.html里面加上和