美文网首页我爱编程
探索webpack源码(三)--- Tapable插件使用 20

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

作者: TinyScript | 来源:发表于2018-04-12 17:01 被阅读0次

    上次说是准备探索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了。:)

    相关文章

      网友评论

        本文标题:探索webpack源码(三)--- Tapable插件使用 20

        本文链接:https://www.haomeiwen.com/subject/mbfohftx.html