案例实战之如何写一个webpack plugin
案例实战之如何写一个webpack plugin
1.写一个生成打包文件目录的file.md文件
// 生成一个目录项目目录的文件夹
class FileListPlugin {
constructor(options) {
this.options = options
}
apply(compiler) {
compiler.hooks.emit.tap('fileListPlugin', (compilation) => {
let assets = compilation.assets
let content = 'In this build:\r\n'
Object.entries(assets).forEach(([fileName, fileSize]) => {
content += `--${fileName} —— ${Math.ceil(fileSize.size() / 1024)}kb\r\n`
})
console.log('====content====', content)
assets[this.options.filename] = {
source() {
return content
},
size() {
return content.length
}
}
})
}
}
module.exports = FileListPlugin
使用
const FileListPlugin = require('./plugins/fileListPlugin.js')
plugins:[
new FileListPlugin({
filename: 'filelist.md'
}),
]
生成的结果如下

2.写一个生成版权信息的copyright文件的插件
class CopyRightWebpackPlugin {
constructor(options) {
this.options = options
}
apply(compiler) {
compiler.hooks.compile.tap('webpackCompiler', () => {
console.log('compiler')
})
compiler.hooks.emit.tapAsync('CopyRightWebpackPlugin', (compilation, cb) => {
compilation.assets[this.options.filename] = {
source() {
return 'copyRight by heibao'
},
size() {
return 25
}
}
cb()
})
}
}
module.exports = CopyRightWebpackPlugin
webpack 的源码compiler钩子函数是借助tapable库实现的
const {
Tapable,
SyncHook,
SyncBailHook,
AsyncParallelHook,
AsyncSeriesHook
} = require("tapable");
class Compiler extends Tapable {
constructor(context) {
super();
this.hooks = {
/** @type {SyncBailHook<Compilation>} */
shouldEmit: new SyncBailHook(["compilation"]),
/** @type {AsyncSeriesHook<Stats>} */
done: new AsyncSeriesHook(["stats"]),
/** @type {AsyncSeriesHook<>} */
additionalPass: new AsyncSeriesHook([]),
/** @type {AsyncSeriesHook<Compiler>} */
beforeRun: new AsyncSeriesHook(["compiler"]),
/** @type {AsyncSeriesHook<Compiler>} */
run: new AsyncSeriesHook(["compiler"]),
/** @type {AsyncSeriesHook<Compilation>} */
emit: new AsyncSeriesHook(["compilation"]),
/** @type {AsyncSeriesHook<string, Buffer>} */
assetEmitted: new AsyncSeriesHook(["file", "content"]),
/** @type {AsyncSeriesHook<Compilation>} */
afterEmit: new AsyncSeriesHook(["compilation"]),
/** @type {SyncHook<Compilation, CompilationParams>} */
thisCompilation: new SyncHook(["compilation", "params"]),
/** @type {SyncHook<Compilation, CompilationParams>} */
compilation: new SyncHook(["compilation", "params"]),
/** @type {SyncHook<NormalModuleFactory>} */
normalModuleFactory: new SyncHook(["normalModuleFactory"]),
/** @type {SyncHook<ContextModuleFactory>} */
contextModuleFactory: new SyncHook(["contextModulefactory"]),
/** @type {AsyncSeriesHook<CompilationParams>} */
beforeCompile: new AsyncSeriesHook(["params"]),
/** @type {SyncHook<CompilationParams>} */
compile: new SyncHook(["params"]),
/** @type {AsyncParallelHook<Compilation>} */
make: new AsyncParallelHook(["compilation"]),
/** @type {AsyncSeriesHook<Compilation>} */
afterCompile: new AsyncSeriesHook(["compilation"]),
/** @type {AsyncSeriesHook<Compiler>} */
watchRun: new AsyncSeriesHook(["compiler"]),
/** @type {SyncHook<Error>} */
failed: new SyncHook(["error"]),
/** @type {SyncHook<string, string>} */
invalid: new SyncHook(["filename", "changeTime"]),
/** @type {SyncHook} */
watchClose: new SyncHook([]),
/** @type {SyncBailHook<string, string, any[]>} */
infrastructureLog: new SyncBailHook(["origin", "type", "args"]),
// TODO the following hooks are weirdly located here
// TODO move them for webpack 5
/** @type {SyncHook} */
environment: new SyncHook([]),
/** @type {SyncHook} */
afterEnvironment: new SyncHook([]),
/** @type {SyncHook<Compiler>} */
afterPlugins: new SyncHook(["compiler"]),
/** @type {SyncHook<Compiler>} */
afterResolvers: new SyncHook(["compiler"]),
/** @type {SyncBailHook<string, Entry>} */
entryOption: new SyncBailHook(["context", "entry"])
};
}}
上面的钩子函数是在webpack解析代码的不同周期执行的
案例实战之如何写一个webpack plugin的更多相关文章
- 案例实战之如何写一个webpack loader
通过以下几个实例掌握webpack loader的写法 1.写一个多语言替换的loader 在index.js在页面上插入了一个{{title}}文本,我们需要在打包的时候将其替换成对应的多语言 fu ...
- 怎样写一个webpack loader
div{display:table-cell;vertical-align:middle}#crayon-theme-info .content *{float:left}#crayon-theme- ...
- 手写一个webpack,看看AST怎么用
本文开始我会围绕webpack和babel写一系列的工程化文章,这两个工具我虽然天天用,但是对他们的原理理解的其实不是很深入,写这些文章的过程其实也是我深入学习的过程.由于webpack和babel的 ...
- 80行代码教你写一个Webpack插件并发布到npm
1. 前言 最近在学习 Webpack 相关的原理,以前只知道 Webpack 的配置方法,但并不知道其内部流程,经过一轮的学习,感觉获益良多,为了巩固学习的内容,我决定尝试自己动手写一个插件. 这个 ...
- Node.JS实战36:写一个WAF中间件!防黑客,防攻击
如果用Node.JS做Web服务,很多时候是会选择Express的. 本文,将展示如何如何实现一个WAF中间件. WAF有什么用? WAF即Web Application Firewall,Web应用 ...
- 图解CSS3核心技术与案例实战(1)
前言: 我买了一本<图解CSS3核心技术与案例实战>大漠写的,为了提高自己的自觉性呢,抓紧看书,把读书笔记放在这上面,跟大家一起分享,也为督促自己完成读书计划. 文末有微信公众号,感谢你的 ...
- 揭秘webpack plugin
前言 Plugin(插件) 是 webpack 生态的的一个关键部分.它为社区提供了一种强大的方法来扩展 webpack 和开发 webpack 的编译过程.这篇文章将尝试探索 webpack plu ...
- YYDS: Webpack Plugin开发
目录 导读 一.cdn常规使用 二.开发一个webpack plugin 三.cdn优化插件实现 1.创建一个具名 JavaScript 函数(使用ES6的class实现) 2.在它的原型上定义 ap ...
- 一个CMS案例实战讲解PHP代码审计入门
前言 php代码审计介绍:顾名思义就是检查php源代码中的缺点和错误信息,分析并找到这些问题引发的安全漏洞. 1.环境搭建: 工欲善其事必先利其器,先介绍代码审计必要的环境搭建 审计环境 window ...
随机推荐
- Java之布尔运算
对于布尔类型boolean,永远只有true和false两个值. 布尔运算是一种关系运算,包括以下几类 比较运算符:>,>=,<,<=,==,!= 与运算 && ...
- 使用 Nginx 阻止恶意 IP 访问
找到具有明显特征的访问记录,比如: /Dec/::: +] "-" "Ouija_x.86/2.0" "-" 也许是某个开源框架的漏洞,执行 ...
- Apache Kafka® is a distributed streaming platform
Kafka Connect简介 我们知道过去对于Kafka的定义是分布式,分区化的,带备份机制的日志提交服务.也就是一个分布式的消息队列,这也是他最常见的用法.但是Kafka不止于此,打开最新的官网. ...
- POJ-排序-归并排序与逆序对
排序:归并排序与逆序对 一.概念 归并排序(MERGE-SORT)是建立在归并操作上的一种有效的排序算法,该算法是采用分治法(Divide and Conquer)的一个非常典型的应用.将已有序的子序 ...
- [转帖][区块链]共识算法(POW,POS,DPOS,PBFT)介绍和心得
[区块链]共识算法(POW,POS,DPOS,PBFT)介绍和心得 置顶 2017-03-12 18:31:19 乐扣老师lekkoliu 阅读数 127953 收藏 更多 分类专栏: 技术管理 区 ...
- 池化方法总结(Pooling)
https://blog.csdn.net/mao_kun/article/details/50507376 在卷积神经网络中,我们经常会碰到池化操作,而池化层往往在卷积层后面,通过池化来降低卷 ...
- linux终端命令行前缀设置为“当前目录”(非绝对路径)
操作 打开家目录下的隐藏文件.bashrc 定位到62行,将小写的\W改为大写,保存即可. 重新打开bash 注意: /etc/profile , /etc/bashrc等文件里的环境变量设置会被.b ...
- Go调用Delphi编写的DLL
参数整数没有问题,但是如果是字符串,要注意几个细节. 记录如下: 1.Delphi定义函数的时候,字符串参数需要使用PChar类型 2.Go传递参数的时候要将字符串转成UTF16的指针,接收的时候采用 ...
- Flanne
容器面临的问题 物理机A上的应用A看到的IP地址是容器A的,是172.17.0.2,在物理机B上的应用B看到的IP地址是容器B的,不巧也是172.17.0.2,当它们都注册到注册中心的时候,注册中心就 ...
- springboot使用HttpSessionListener 监听器统计当前在线人数
概括: request.getSession(true):若存在会话则返回该会话,否则新建一个会话. request.getSession(false):若存在会话则返回该会话,否则返回NULL ht ...