1 基本概念
1.1 核心概念
- entry入口
str/单入口:打包形成一个chunk,输出一个bundle --常用
arr/多入口:形成一个chunk,输出一个bundle
obj/多入口:形成多个chunk,输出多个bundle --常用
- output输出
filename:文件名
path:文件夹名称
- loader翻译(非js文件)
- plugins更广任务
- mode(dev+prod)
1.2 运行
- 下载webpack webpack-cli
- webpack.config.js:webpack配置文件
-
webpack编译后会生成文件;npx webpack-dev-server只会在内存中编译打包
module.exports={
entry:入口,
output:出口,
module:loader,
plugins:插件,
mode:devlopment,
devServer:{},//运行代码目录;gzip压缩;端口号;域名;自动打开浏览器;热膜替换;监视文件变化重载;不需要日志;出错不要全屏提示;服务器代理解决开发环境跨域
devtool:source-map,
optimization:splitChunks配置;runtimeChunk配置:将当前模块的记录其他模块的hash单独打包为一个文件runtime---解决index引入a.js,修改导致a文件修改index文件的contenthash变化;minimizer配置:terser-webpack-plugin---压缩js
externals:jq,
resolve:配置路径别名;省略路径后缀名;告诉webpack解析模块如node_modules去找哪个目录,
}
注意:引入叫trunk,输出叫bundle。
以下均为webpack4,webpack5自动实现tree shaking;构建后文件变小。
2 开发环境配置
2.1 打包样式资源
style-loader:创建style标签,插入JS到head中
css-loader:css文件加载到JS中
less-loader:less文件编译成css文件(还需要下载less)
2.2 打包html资源
html-webpack-plugin:安装-引入-配置:创建一个空html文件,自动引入打包后的文件如build.js
2.3 打包图片资源
方式一:.js引入.less,.less引入图片(html文件会自动引入)
url-loader:图片小于8KB,base64处理,减少请求数量(需要file-loader )--es6模块化解析
方式二:.html中引入图片
html-loader:用于引入图片,从而被url-loader处理--commonJS解析
问题:解析方式不同,需要将es6关闭
2.4 打包其他资源
下载iconfont--.js中引入iconfont相关文件
需要file-loader
2.5 devServer
自动编译,自动打开并刷新浏览器。
3 生产环境配置
3.1 提取css成单独文件
style-loader去掉 css-loader
min-css-extract-plugin:提取js中的css成单独文件
3.2 css兼容性处理(扩展前缀)
postcss-loader:
postcss-preset-env:找到package.json中browserslist里的配置,加载指定css兼容样式(不同浏览器)
注意:默认为生产环境,需要设置nodejs环境变量修改为开发环境
3.3 压缩css
optimize-css-assets-webpack-plugin:体积变小
3.4 js语法检查
eslint-loader/eslint:只检查自己写的源代码,排除node_modules,配置自动修复fix:true
eslint-config-airbnb-base/eslint-plugin-import/eslint:package.json中设置eslint规则继承airbnb
3.5 js兼容性处理
babel-loader @babel/core @babel/preset-env:es6转为es5,只能转换基本语法,promise不行
@babel/polyfill:promise可以,兼容性代码全部引入,体积太大
core-js:按需加载兼容性代码,体积小
注意:一个文件被多个loader处理,先执行eslint,再babel
module中配置oneOf:所有loader只匹配一个,将eslint-loader提取出去
3.6 压缩js /html
mode:production:会自动压缩js
html-webpack-plugin中添加minify配置:压缩html,移除空格和注释
4 性能优化
4.0 概念
开发:打包速度HMR、代码调试sourceMap
生产:打包速度oneOf、babel缓存、多进程打包、externals、dll、
代码性能:文件资源缓存、tree shaking、code split、懒加载、pwa
4.1 开发环境
4.1.1HMR(热模替换)
npx xxx 启动开发环境配置---修改代码,整个页面会重新刷新
devServer中开启hot---一个模块变化,只重新打包这个模块
样式文件:style-loader内部实现了
js文件:默认没有HMR功能---修改index.js中的代码,根据hot属性存在,监听模块文件变化更新(只能处理非入口文件)
html文件:导致不能使用HMR功能--修改entry入口,将html文件引入,整体页面刷新(一个文件不需要)
4.1.2 sourceMap(定位代码错误位置)
配置devtool:source-map---提供源代码到构建后代码的映射技术,打包后生成js文件
开发环境:速度快,调试好 eval-source-map
生产环境:源代码隐藏,调试友好 source-map
4.2 生产环境
4.2.1 缓存
babel缓存:babel-loader中配置cacheDirectory---第二次构建读取缓存
文件资源缓存:server.js用express搭建服务器引入built静态资源--被强制缓存
--将构建后的文件名加hash值(js和css使用同一个hash),所有缓存失效
---chunkhash(js和css使用同一个hash)同一个入口就会打包
---contentHash(内容改变重新打包)
4.2.2 tree shaking(去除没有使用的代码)
前提:使用es6模块化;开启production环境
注意:package.json中配置sideEffects:false(所有代码都可以tree shaking)。
可能把打包后的css文件去掉,需要配置sideEffects:["*.css"]
4.2.3 code split(文件分割,按需加载)
方式一:
多入口entry,并修改输出后的文件名,输出相应个数的bundle(多次加载jquery)
方式二:
配置optimization中splitChunks,node_modules代码单独打包一个chunk输出(单入口,如jq)
配置optimization中splitChunks,自动分析多入口chunk中,有没有公共的文件,如果有会打包成单独一个chunk(多入口,如jq)
方式三:(推荐)
index.js中引入test.js会打包成1个chunk---需要import(引入test).then().catch()实现两个文件单独打包(单入口)
4.2.4 懒加载
index.js中引入test.js---两个文件都加载
import().then()(点击按钮的时候加载)---文件需要时加载
import中配置,test预加载prefetch---文件使用之前提前加载,其他资源加载完毕,浏览器空闲时加载,兼容性较差
4.2.5 PWA(离线访问)
workbox-webpack-plugin:serviceworker快速启动,并生成相关配置文件
注意:eslint不认识navigator,需要修改package.json中的相关配置
serviceworker代码必须运行在服务器上 ,兼容性差
4.2.6 多进程打包
thread-loader:应用于babel-loader,进程启动需要600ms,不要滥用
4.2.7 externals
externals:配置忽略的库名,如JQ---需要CDN引入
4.2.8 dll(对某些库单独打包成不同chunk--react/vue)
webpack.dll.js :打包生成了个manifest.json文件,用来提供和JQ映射
运行代码webpack --config webpack.dll.js
webpack.config.js中引入manifest.json文件,不需要再打包jq
add-asset-html-webpack-plugin:将某个文件打包输出出去,并在html中自动引入该资源