1. source-map的设置(错误提示)
- devtool
1.1 开发模式使用:cheap-module-source-map
- 打包编译速度更快,只映射到行,
1.2 生产环境使用:source-map
- 因为生产环境的代码会压缩,所以必须映射到行和列的信息
2. HMR(只能在开发环境下使用)
-
webpack的默认行为会在一个模块发生变化的时候把所有模块都重新打包
-
开启HMR功能后,只重新打包变化的模块,其它模块使用缓存
-
样式文件天然支持这个功能(devserver 的hot配置默认为true)
-
js的支持:(vue-loader和react-loader都默认支持了这样的功能,不需要我们单独实现)
-
if(module.hot) { module.hot.accept('./xx.js') // 被引入的模块发生变化时,就会启用热模块更新 }
3. oneOf
-
webpack的默认行为是当一个类型的检查是否使用某一个loader进行处理时,即使匹配到了也会在接下来的所有规则中进行再次匹配(走完所有的rules规则匹配)
-
使用oneOf解决上面的问题
-
rules: [ { oneOf:[ ...rules ] } ]
4. 所有文件处理范围(include和exclude)
-
两个配置只能同时是用一个,可以设置包含(include)或者设置排除(exclude)
-
一般对js处理(babel和eslint比较耗时),因为代码量比较大
-
// loader 的配置 { test: /\.js$/, exclude: /(node_modules)/, // 使用这种 include: path.join(__dirname, 'src'), // 或者使用这种 use: [...] } // 插件的配置 new ESLintPlugin({ context: path.join(__dirname, 'src'), // 配置eslint检测范围 exclude: 'node_modules' // 这是一个默认值 }),
5. webpack缓存的使用
-
前面提到js文件的编译需要进行babel和eslint的处理,比较耗时,所有这里说的缓存也只针对这两个过程
-
bebel-loader 配置
-
{ loader: 'babel-loader?', options: { cacheDirectory: true, // 开启babel缓存 cacheCompression: false // 关闭缓存文件压缩(耗时无意义,线上用不到) } }
-
eslint 配置
-
new ESLintPlugin({ context: path.join(__dirname, 'src'), // 配置eslint检测范围 exclude: 'node_modules', // 这是一个默认值 cache: true, // 开启缓存 cacheLocation: path.resolve(__dirname, './node_modules/.cache/eslint') // 设置缓存目录 }),
6. 多进程打包(大数据量的项目才去使用)
-
注意: 把注意写在前面,每个进程打开大概需要 600ms 的时间,建议在文件量很大的情况下使用
-
一样是针对最耗时的任务 js 处理 babel 和 eslint 检查使用
-
安装依赖(用于babel编译开启多进程)
-
npm install thread-loader -D
-
获取 cpu 核心数量
-
const os = require('os') const threads = os.cpus().length
-
增加多进程配置添加到 babel-loader 前面
-
{ test: /\.js$/, exclude: /(node_modules)/, // 设置哪些目录不需要扫描 use: [ { loader: 'thread-loader', // 开启多线程处理 babel options: { works: threads // 设置线程数量 } }, { loader: 'babel-loader?cacheDirectory', //开启缓存,可以设置缓存目录 } ] }
-
引入 webpack5 内置压缩 js 代码的插件
-
const TerserWebpackPlugin = require('terser-webpack-plugin')
-
js代码压缩开启多进程
-
plugins: [ new TerserWebpackPlugin({ parallel: threads // js 代码压缩开启多进程,threads:cpu 核心数量 }) ] // 或者放入optimization中,和之前的 css 压缩一样 optimization: { minimizer: [ new CssMinimizerPlugin(), new TerserWebpackPlugin({ parallel: threads // js 代码压缩开启多进程,threads:cpu 核心数量 }) ] }
-
eslint 开启多进程
-
new ESLintPlugin({ context: path.join(__dirname, 'src'), // 配置eslint检测范围 exclude: 'node_modules', // 这是一个默认值 cache: true, // 开启缓存 cacheLocation: path.resolve(__dirname, './node_modules/.cache/eslint') // 设置缓存目录 + threads, // +++ eslint 开启多进程 }),
7. tree-shaking
- webpack 内置了这个功能,生产模式下自动打开
- tree shaking 依赖于 esm实现,commonjs 语法不支持
8. 图片压缩
-
依赖安装1
npm install image-minimizer-webpack-plugin -D
-
无损压缩依赖
-
npm install imagemin-gifsicle imagemin-jpegtran imagemin-optipng imagemin-svgo --save-dev
-
有损压缩依赖
-
npm install imagemin-gifsicle imagemin-mozjpeg imagemin-pngquant imagemin-svgo --save-dev
-
配置
-
// webpack.config.js const ImageMinimizerPlugin = require("image-minimizer-webpack-plugin"); const { extendDefaultPlugins } = require("svgo"); plugins: [ new ImageMinimizerPlugin({ minimizerOptions: { // Lossless optimization with custom option // Feel free to experiment with options for better result for you plugins: [ ["gifsicle", { interlaced: true }], ["jpegtran", { progressive: true }], ["optipng", { optimizationLevel: 5 }], // Svgo configuration here https://github.com/svg/svgo#configuration [ "svgo", { plugins: extendDefaultPlugins([ { name: "removeViewBox", active: false, }, { name: "addAttributesToSVGElement", params: { attributes: [{ xmlns: "http://www.w3.org/2000/svg" }], }, }, ]), }, ], ], }, }), ],
-
这种方式的依赖安装问题比较大
-
也可以使用第二种方式完成图片压缩:
-
安装依赖
-
npm install @squoosh/lib --save-dev
-
有损压缩:
-
// 引入依赖 const ImageMinimizerPlugin = require("image-minimizer-webpack-plugin"); // 使用插件(放入plugins) new ImageMinimizerPlugin({ minimizer: { implementation: ImageMinimizerPlugin.squooshMinify, options: { // Your options for `squoosh` }, }, }), // 再说一次还可以在 optimization 中使用 optimization: { minimizer: [ new ImageMinimizerPlugin({ minimizer: { implementation: ImageMinimizerPlugin.squooshMinify, options: { // Your options for `squoosh` }, }, }), ], },
-
无损压缩
-
optimization: { minimizer: [ new ImageMinimizerPlugin({ minimizer: { implementation: ImageMinimizerPlugin.squooshMinify, options: { encodeOptions: { mozjpeg: { // That setting might be close to lossless, but it’s not guaranteed // https://github.com/GoogleChromeLabs/squoosh/issues/85 quality: 100, }, webp: { lossless: 1, }, avif: { // https://github.com/GoogleChromeLabs/squoosh/blob/dev/codecs/avif/enc/README.md cqLevel: 0, }, }, }, }, }), ], },