loaders 与 plugin 的区别
loaders: loaders 是文件加载器,能够加载资源文件,并对 这些文件进行处理,例如,编译,压缩等,最终一起打包到指定文件 中。(链式调用:多个 Loader 可以串联执行(如 sass-loader → css-loader → style-loader))
- 转换文件内容:将非 JS 文件(如 .css、 .vue)转换成 Webpack 可识别的模块。
- 链式调用:多个 Loader 可以串联执行(如 sass-loader → css-loader → style-loader)
plugin: 在 webpack 运行的生命周期会有许多事件,plugin 可以监听这些事件
区别:加载器是用来加载文件的,webpack 本身只能加载 js 文件(内 置 babel-loader),加载其他文件就需要安装别的 loader,比如: css-loader file-loader Plugin 是扩展 webpack 功能的,通过 plugin ,webpack 可以实 现 loader 不能完成的复杂功能
打包原理
Webpack 是把项目当做一个整体,通过给定一个主文件,webpack 将从这个主文件开始找到项目中所有依赖的文件,使用 loaders 类处 理,最后打包成一个或者多个浏览器可识别的 js 文件
从启动到结束会依次执行以下三大步骤:
- 初始化流程:从配置文件和 Shell 语句中读取与合并参数,并初始化需要使用的插件和配置插件等执行环境所需要的参数
- 编译构建流程:从 Entry 发出,针对每个 Module 串行调用对应的 Loader 去翻译文件内容,再找到该 Module 依赖的 Module,递归地进行编译处理
- 输出流程:对编译后的 Module 组合成 Chunk,把 Chunk 转换成文件,输出到文件系统
提高构建速度
- 优化 loader 配置
- 合理使用 resolve.extensions
- 优化 resolve.modules
- 优化 resolve.alias
- 使用 DLLPlugin 插件
- 使用 cache-loader
- terser 启动多线程
- 合理使用 sourceMap
HMR 热更新
- 通过webpack-dev-server创建两个服务器:提供静态资源的服务(express)和Socket服务
- express server 负责直接提供静态资源的服务(打包后的资源直接被浏览器请求和解析)
- socket server 是一个 websocket 的长连接,双方可以通信
- 当 socket server 监听到对应的模块发生变化时,会生成两个文件.json(manifest文件)和.js文件(update chunk)
- 通过长连接,socket server 可以直接将这两个文件主动发送给客户端(浏览器)
- 浏览器拿到两个新的文件后,通过HMR runtime机制,加载这两个文件,并且针对修改的模块进行更新
