# 插件开发

# 概述

插件向第三方开发者提供了 webpack 引擎中完整的能力。使用阶段式的构建回调,开发者可以引入它们自己的行为到 webpack 构建流程中。创建插件比创建 loader 更加高级,因为你将需要理解一些 webpack 底层的内部特性来做相应的钩子,所以做好阅读一些源码的准备!

# 简单的例子

一个简单的例子,在 rundone 两个生存周期中输出日志。

# 插件的开发

// plugins/test.js
const pluginName = 'ConsolePlugin';

var ConsolePlugin = function ConsolePlugin() {
    console.log('初始化插件')
};

ConsolePlugin.prototype.apply = function(compiler) {
    compiler.hooks.run.tap(pluginName, c => {
        console.log("webpack 构建过程开始");
    });
    compiler.hooks.done.tap(pluginName, stats => {
        console.log('hello world');
    })
};

module.exports = ConsolePlugin;

# 插件的引用

// webpack.config.js
const ConsolePlugin = require('../plugins/test');
module.exports = {
    plugins: [
        new ConsolePlugin()
    ]
};

# Compiler 和 Compilation

# Compiler

对象代表了完整的 webpack 环境配置。这个对象在启动 webpack 时被一次性建立,并配置好所有可操作的设置,包括 options,loader 和 plugin。

# Compilation

对象代表了一次资源版本构建。当运行 webpack 开发环境中间件时,每当检测到一个文件变化,就会创建一个新的 compilation,从而生成一组新的编译资源。一个 compilation 对象表现了当前的模块资源、编译生成资源、变化的文件、以及被跟踪依赖的状态信息。compilation 对象也提供了很多关键时机的回调,以供插件做自定义处理时选择使用。

# 插件类型

基于 tapable 库,可以仔细阅读一番。

# 同步 SyncHook

使用 new SyncHook([params]) 声明, 使用 tap 来绑定

# 同步 Bail Hooks

使用 SyncBailHook[params] 声明, 使用 tap 来绑定

如果返回值不是 undefined 就不会继续向下执行其他的钩子方法

# 同步 Waterfall Hooks

使用 SyncWaterfallHook[params] 声明, 使用 tap 来绑定

前一个插件执行完成后,返回值作为参数,执行下一个插件

# 异步 Async Series Hook

使用 AsyncSeriesHook[params] 声明, 使用 tap / tapAsync / tapPromise 来绑定

# 异步 Async waterfall

使用 AsyncWaterfallHook[params] 声明, 使用 tap / tapAsync / tapPromise 来绑定

# 异步 Async Series Bail

使用 AsyncSeriesBailHook[params] 声明, 使用 tap / tapAsync / tapPromise 来绑定

# 异步 Async Parallel

使用 AsyncParallelHook[params] 声明, 使用 tap / tapAsync / tapPromise 来绑定