我爱编程

探索webpack源码(三)--- Tapable插件使用 20

2018-04-12  本文已影响0人  TinyScript

上次说是准备探索Compiler.js,但是我看了一下Compiler.js里面最主要的也就是用的Tapable,所以就先鸽大家一下了[手动笑哭]。

这里不得不先吐槽一下,之前学习Tapable的时候,基本只有Tapable 0.2的教学版本,而webpack4.x用的又是Tapable 1.x,学起来真的是有种学医救不了中国人的感觉…但是最近webpack中文文档更新的很快,好像半个月就更新了3个版本webpack v4.2 -> webpack v4.5,总算是开始维护自己的文档了。

不废话那么多了,进入主题吧。


Tapable

按照上一次我们说的Compiler.js,这次我们还是过一下吧,不过只到定义类的那一行:

class Compiler extends Tapable {
  // something code ...
}

好的,这里的Compiler继承了Tapable,然后再往上找一下就能发现一段引入代码:

const Tapable = require('tapable').tapable

今天探索就是讲这一部分,只是探索怎么使用而不是探索源码,因为tapable体系特别复杂,没办法一次性讲清楚。

其实用法主要就只有以下三种:

针对于同步:
  tap对应call
针对于异步:
  tapSync对应promise
  tapAsync对应callAsync

而使用方法基本就是这样,以同步为例:

const { SyncHook } = require('tapable');
const hook = new SyncHook();
hook.tap('my-hook', () => {
  console.log('我的hook。')
});
hook.call(); 
// 我的hook

而需要给hook添加参数:

const { SyncHook } = require('tapable');
const hook = new SyncHook(['参数1', '参数2', '参数3']);
hook.tap('my-hook', (arg1, arg2, arg3) => {
  console.log(arg1, arg2, arg3)
});
hook.call('小红', '小绿', '小蓝')
// 小红 小绿 小蓝

原本是没有打算写Async的,但是自己也经常忘记Async的用法,懒得老是去写代码测试,就在这里也补上吧。

const { AsyncSeriesHook } = require('tapable');
const hook1 = new AsyncSeriesHook(['arg']);
const hook2 = new AsyncSeriesHook(['arg']);
const hook3 = new AsyncSeriesHook(['arg']);

hook1.tapPromise('asyncHook', (arg) => {
  console.log(arg)
  return Promise.resolve();
})

hook1.promise('exec promise tap hook!').then(() => {
  // then函数这里似乎无法接收从tapPromise的resolve传过来的内容。
  // 所以then接收的匿名函数没有传参。
  console.log('执行后续内容。')
});
// 打印:
// exec promise tap hook!
// 执行后续内容。

hook2.tapAsync('asyncHook', (arg) => {
  console.log(arg);
})

hook2.callAsync('exec async tap hook!');
// 打印:
// exec async tap hook!

// 这里还有个隐藏技能,可能是我没去仔细tapable看源码的缘故吧
// 用tap绑定的AsyncSeriesHook,在callAsync的时候还会接收一个err-first格式的回调。
hook3.tap('asyncHook', (arg) => {
  console.log(arg);
})

hook3.callAsync('exec tap hook!', err => { console.log(123) })

由于tapAsync比tapPromise简单,所以内容也比较少,但是他们似乎不可覆盖使用,也就是一个AsyncSeriesHook不能同时绑定async和promise,否则promise似乎会不生效,这里我没有仔细往下试,我想设计的人也不会想我们这么用的吧(笑哭)。


以上就是hook的使用方式,除了SyncHook和AsyncSeriesHook以外,还有以下的Hook:

name desciption
SyncHook 同步钩子
SyncBailHook 同步保留钩子(有返回值)
SyncWaterfallHook 同步瀑布流钩子(执行完call以后,以最后一个返回值为准)
SyncLoopHook 暂时没见过
AsyncParallelHook 异步并行钩子
AsyncParallelBailHook 异步并行保留值钩子
AsyncSeriesHook 异步串行钩子
AsyncSeriesBailHook 异步串行保留值钩子
AsyncSeriesWaterfallHook 异步串行瀑布流钩子

以上就是 Tapable 钩子的探索,这里只讲了同步调用的办法,异步的用法在开头也已经说了有对应的方法,接下来就可以开始讲Compiler.js了。:)

上一篇下一篇

猜你喜欢

热点阅读