关于构建工具,我用过的也就webpack,gulp稍微有些了解,可是没在项目中真正用到。以个人理解,构建工具能实现的功能:css
1. 代码转换: 从typescript->JavaScript,sass->css等;vue
2. 代码优化: 压缩HTML、css代码等;node
3. 代码分割: 将通用的代码从多个文件中抽取出来;大文件切割成小文件;webpack
4. 模块合并: 模块化项目里会有不少模块,好比一个模块引用了另外一个模块这样子。构建工具能够将多个模块合并成一个模块;web
5. 自动刷新: 监听代码的变化,对代码进行实时刷新;typescript
6. 在代码提交到代码仓库以前进行代码校验,看是否符合规范或者单元测试是否经过;element-ui
7. 自动发布: 代码更新完毕以后,自动构建发布代码并传输给发布系统进行发布。json
关于webpack的做用,官网的一个图其实就说明了一切。gulp
webpack是一个打包模块化JavaScript的工具。在webpack里一切文件皆模块。这样的好处是能够清楚的了解各模块之间的依赖关系,以便webpack进行组合与打包。打包的过程当中:经过loader将webpack不能处理的文件转换成它能处理的文件,而后再经过plugins进行功能的扩展,好比压缩文件、分割文件的处理等,而后进行打包。sass
1. 专一于模块化项目;
2. plugins能作的事情很是多;
3. 社区活跃。
一、官方文档很是难懂,不利于学习;
2. plugins繁多,须要不断的学习才能灵活掌握;
3. 对初学者不利,调试很难定位问题。。
mode: 模式。在webpack4新引入的。能够配置成production、development两种值,而单元测试也属于开发模式下的。
entry: 入口。webpack执行的构建的第一步。
entry: {
// 入口 (多个文件做为一个入口 全局使用babel-polyfill polyfill将会被打包进这个入口文件中, 并且是放在文件最开始的地方)
app: ['babel-polyfill', './src/main.js']
}复制代码
上面的例子是单页面项目配置的入口,只有一个入口文件,而babel-polyfill是一个转换js标准的工具,再加上.babelrc里的配置,就能够实现js标准处理
module: webapck中一切皆模块,webapck会从entry开始递归找到全部的依赖。在module.rules里进行loader的配置
module: {
rules: [{
test: /\.js$/,
loader: 'babel-loader', // js处理
include: [ // Rule.include 是 Rule.resource.include 的简写。若是你提供了 Rule.include 选项,就不能再提供 Rule.resource
resolve('src'),
resolve('test'),
resolve('node_modules/webpack-dev-server/client')
]
},
...
]
}复制代码
devtool: 用哪种sourceMap来处理。sourceMap的概念,简单理解,就是咱们写的代码,在通过构建工具的处理后,若是在调试的时候出现什么错误,因为代码已经进行过了处理,若果不在处理前就标记好代码的各类信息,处理后没法定位问题,而sourceMap就是作标记的工做。好比说标记代码的行信息,列信息等等。用不一样的模式下的souceMap,获得的代码信息不太同样。
devtool: config.build.productionSourceMap ? config.build.devtool : false,复制代码
resolve: 模块解析的相关配置。好比文件查找的优先级等
resolve: {
// 模块解析相关的配置
extensions: ['.js', '.vue', '.json'], // 这里的顺序表明匹配后缀的优先级,例如对于 index.js 和 index.jsx,会优先选择 index.js
alias: { // 若是咱们有某个模块及其经常使用,常常编写相对路径很麻烦,就能够在此处配置某个模块的别名
'@': resolve('src')
}
},复制代码
performance: {
hints: 'warning', // 警告 室还有一个值是error
maxAssetSize: 30000000, // 整数类型(以字节为单位) 资源(asset)是从 webpack 生成的任何文件。此选项根据单个资源体积,控制 webpack 什么时候生成性能提示。默认250000 maxEntrypointSize: 50000000 // 整数类型(以字节为单位) 默认250000 此选项根据入口起点的最大致积,控制 webpack 什么时候生成性能提示
}复制代码
plugins: 配置插件
plugins: [
new minCssExtractPlugin({ // 该插件用于将css提取到单独的文件,以便多个页面共享一个css文件
filename: utils.assetsPath('css/[name].[contenthash:8].css'),
chunkFilename: utils.assetsPath('css/[name].[contenthash:8].css')
})
]复制代码
optimization: { // 优化
splitChunks: { // 动态导入模块,webpack4+的全新通用分块策略配置
chunks: 'all',
cacheGroups: {
libs: {
name: 'chunk-libs',
test: /[\\/]node_modules[\\/]/,
priority: 10,
chunks: 'initial' // 只打包初始时依赖的第三方
},
elementUI: {
name: 'chunk-elementUI', // 单独将 elementUI 拆包
priority: 20, // 权重要大于 libs 和 app 否则会被打包进 libs 或者 app
test: /[\\/]node_modules[\\/]element-ui[\\/]/
}
}
},
runtimeChunk: 'single', // 值 "single" 会建立一个在全部生成 chunk 之间共享的运行时文件
minimizer: [ //容许你经过提供一个或多个定制过的 TerserPlugin 实例,覆盖默认压缩工具(minimizer)。
new UglifyJsPlugin({
uglifyOptions: {
mangle: { // 混淆
safari10: true
}
},
sourceMap: config.build.productionSourceMap, // 编译后代码对源码的映射,用于网页调试
cache: true,
parallel: true
}),
// 压缩提取的CSS。使用此插件减小来自不一样组件的可能重复的CSS
new OptimizeCSSAssetsPlugin()
]
}复制代码
output: 通过一系列处理,获得想要的结果。
output: {
path: config.build.assetsRoot,
filename: utils.assetsPath('js/[name].[chunkhash:8].js'),
chunkFilename: utils.assetsPath('js/[name].[chunkhash:8].js')
},复制代码
Webpack 在启动后会从 Entry里配置的 Module 开始,递归解析 Entry 依赖的全部 Module 每找到一个 Module ,就会根据配置的 Loader 去找出对应的转换规则,对 Module 进行转换后, 再解析出当前 Module 依赖的 Module 这些模块会以 Entry为单位进行分组, Entry 及其 全部依赖的 Module 被分到 个组也就是 Chunk 。最后, Webpack 将全部 Chunk 转换成 文件输出。在整个流程中, Webpack 会在恰当的时机执行 Plugin 义的逻辑。