class MyExampleWebpackPlugin {
apply(compiler) {
compiler.hooks.emit.tapAsync(
'MyExampleWebpackPlugin',
(compilation, callback) => {
console.log('This is an example plugin!');
console.log(Here’s the `compilation` object which represents a single build of assets:', compilation);
compilation.addModule(/* ... */);
callback();
}
)
}
}
class HelloCompilationPlugin {
apply(compiler) {
// Tap into compilation hook which gives compilation as argument to the callback function
compiler.hooks.compilation.tap('HelloCompilationPlugin', (compilation) => {
// Now we can tap into various hooks available through compilation
compilation.hooks.optimize.tap('HelloCompilationPlugin', () => {
console.log('Assets are being optimized.');
});
});
}
}
module.exports = HelloCompilationPlugin;
原文: https://webpack.js.org/contribute/writing-a-plugin/ demo: https://github.com/FrankKai/webpack-plugin-demo
什么是插件
插件是webpack引擎开放给第三方开发者的一种潜力机制。使用分阶段构建callback,开发者可以引进自己的行为到webpack构建进程。比起构建loader,构建插件更加高级一些,因为你需要理解一些webpack底层内部的hook。做好看源码的准备!
新建一个插件
一个webpack插件,由以下这些内容组成:
插件的基础架构
插件是原型链上有apply方法的实例化对象。这个apply方法会在webpack编译器安装插件时,调用一遍。 apply方法暴露出了webpack底层编译器的引用,可以赋权给编译器callback。
一个插件的结构如下:
为了使用这个插件,需要在你的webpack插件配置的plugins增加一个实例。
可以通过schema-utils约束webpack插件配置的传参:
compiler和compilation
开发插件最重要的2个对象:compiler对象,compilation对象。
理解它们是扩展webpack引擎的最重要的一步。
更多compiler和compilation的hook,可以看https://webpack.js.org/api/plugins/
异步事件hook
有一些插件hook是异步的。我们可以使用tabAsync或者tabPromise去同步的使用tap。
tabAsync
当我们使用tabAsync方法去接进插件时,我们需要调用回调函数抛出来的callback函数。
tabPromise
使用tabPromise也可以处理异步tap,需要返回一个promise。
示例
了解了webpack compiler以及每个独立的编译步骤后,我们可以为引擎做的事,是无穷大的。我们可以重新格式化已经存在的文件,创建派生文件,或者生产全新的资源。
我们现在创建一个生成assets.md的文件,生成我们每次构建产生的静态文件。