webpack 的本质就是 tapable
2023-10-03 03:51:28
webpack 本质上就是一个事件中心,管理各种各样的事件,这些事件通常是由插件触发的。webpack 把所有需要做的事件都抽象成一个个的钩子(Hook),也就是注册什么就执行什么这么简单的逻辑。
同步和异步
我们知道 webpack 有三种钩子类型:sync、async、promise。同步钩子是当前正在做的事情必须马上执行,而异步钩子和 promise 钩子是当前正在做的事情可以放到下个 tick 再执行。所以,对于 webpack 的同步钩子,执行顺序必须按照注册的顺序执行。对于 webpack 的异步钩子和 promise 钩子,执行顺序不一定严格按照注册的顺序执行。
如何理解 tapable
webpack 是基于 tapable 这个模块构建的,tapable 本质上就是一个发布/订阅模式,或者说事件监听器模式。在 tapable 中,事件的发布者称为插件(Plugin),事件的订阅者称为 tap。
每个 tap 都对应一个回调函数,当插件触发事件时,就会调用这些回调函数。回调函数可以是同步的,也可以是异步的。
tap* 方法
在 tapable 中,我们可以使用 tap* 方法来注册 tap。其中,* 可以是 sync、async 或 promise,分别对应同步 tap、异步 tap 和 promise tap。
例如,我们可以使用以下代码来注册一个同步 tap:
plugin.tap('event', (arg1, arg2) => {
// do something
});
我们可以使用以下代码来注册一个异步 tap:
plugin.tapAsync('event', (arg1, arg2, callback) => {
// do something
callback();
});
我们可以使用以下代码来注册一个 promise tap:
plugin.tapPromise('event', (arg1, arg2) => {
return new Promise((resolve, reject) => {
// do something
resolve();
});
});
call 方法
当插件触发事件时,tapable 会调用所有已注册的 tap。在调用 tap 时,tapable 会把事件的参数传递给 tap 的回调函数。
例如,我们可以使用以下代码来触发一个事件:
plugin.call('event', arg1, arg2);
总结
webpack 本质上就是一个事件中心,管理各种各样的事件。webpack 把所有需要做的事件都抽象成一个个的钩子(Hook),也就是注册什么就执行什么这么简单的逻辑。
webpack 中的钩子分为三种类型:sync、async 和 promise。同步钩子是当前正在做的事情必须马上执行,而异步钩子和 promise 钩子是当前正在做的事情可以放到下个 tick 再执行。
我们可以使用 tapable 中的 tap* 方法来注册 tap。我们可以使用 plugin.call 方法来触发事件。