.scss 或 .yaml。在打包器中,插件可以实现框架级功能,例如 CSS 提取、宏以及客户端与服务器代码共置。
生命周期钩子
插件注册在打包生命周期的不同阶段运行的回调:onStart():打包器开始构建时运行一次onResolve():模块解析之前运行onLoad():模块加载之前运行onBeforeParse():在文件被解析之前,在解析线程中运行零拷贝的本地插件onEnd(): 打包完成后运行。
参考
类型的概览(完整的类型定义请参阅 Bun 的bun.d.ts):
bun.d.ts
用法
插件是一个具有name 属性和 setup 函数的 JavaScript 对象。
myPlugin.ts
Bun.build 时,将其传入 plugins 数组。
index.ts
插件生命周期
命名空间
onLoad 和 onResolve 接受一个可选的 namespace 字符串。
每个模块都有一个命名空间。命名空间会为转译代码中的导入添加前缀;例如,一个具有 filter: /\.yaml$/ 和 namespace: "yaml:" 的加载器,会将从 ./myfile.yaml 的导入转换为 yaml:./myfile.yaml。
默认命名空间是 "file",无需指定:import myModule from "./my-module.ts" 等同于 import myModule from "file:./my-module.ts"。
其他常见命名空间:
"bun":用于 Bun 特有的模块("bun:test"、"bun:sqlite")"node":用于 Node.js 模块("node:fs"、"node:path")
onStart
index.ts
onStart() 回调完成才继续。
例如:
index.ts
onStart() 回调完成:10 秒的休眠以及向 bundle-time.txt 写入内容。
onStart() 回调(与其他所有生命周期回调一样)不能修改 build.config 对象。要修改
build.config,请直接在 setup() 函数中进行。onResolve
onResolve() 插件生命周期回调配置模块的解析方式。
onResolve() 的第一个参数是一个包含 filter 和 namespace 属性的对象。filter 是一个用于匹配导入字符串的正则表达式。两者结合起来,用于选择应用自定义解析逻辑的模块。
onResolve() 的第二个参数是一个回调,当 Bun 找到与第一个参数中定义的过滤器和命名空间匹配的模块导入时,该回调会针对每个模块导入执行一次。
回调会接收匹配模块的路径,并可以为该模块返回一个新路径。Bun 会读取新路径的内容,并将其解析为模块。
例如,将所有导入 images/ 的模块重定向到 ./public/images/:
index.ts
onLoad
onLoad() 插件生命周期回调会在 Bun 读取并解析模块之前修改模块的内容。
与 onResolve() 类似,onLoad() 的第一个参数用于选择此次 onLoad() 调用所应用的模块。
onLoad() 的第二个参数是一个回调,在 Bun 将匹配的模块内容加载到内存之前,该回调会针对每个匹配的模块执行一次。
回调会接收匹配模块的路径、其命名空间、默认加载器以及一个 defer 函数。
回调可以返回该模块新的 contents 字符串和新的 loader。
例如:
index.ts
import env from "env" 的导入转换为一个导出当前环境变量的 JavaScript 模块。
.defer()
传递给onLoad 回调的参数之一是一个 defer 函数。它会返回一个 Promise,该 Promise 会在所有其他模块加载完成后解析。当模块的内容依赖于其他模块时,请等待该 Promise。
示例:跟踪和报告未使用导出
示例:跟踪和报告未使用导出
index.ts
原生插件
Bun 的打包器使用原生代码编写,并使用多个线程并行加载和解析模块。JavaScript 插件运行在单个线程上,因为 JavaScript 本身是单线程的。 原生插件是暴露生命周期钩子(C ABI 函数)的 NAPI 模块。它们可以在多个线程上运行,因此比 JavaScript 插件运行得快得多,并且可以跳过将字符串传递给 JavaScript 所需的 UTF-8 -> UTF-16 转换等工作。 原生插件可以使用以下生命周期钩子:onBeforeParse():在任何线程上,文件被 Bun 打包器解析前调用。
用 Rust 创建原生插件
terminal
terminal
lib.rs 中,使用 bun_native_plugin::bun 过程宏定义实现原生插件的函数。
下面是一个实现 onBeforeParse 钩子的示例:
lib.rs
Bun.build() 中使用它:
index.ts
onBeforeParse
onBeforeParse() 回调会在 Bun 的打包器解析文件前立即运行。
它接收文件内容,并可以选择返回新的源代码。
Bun 可以从任何线程调用此回调,因此 NAPI 模块的实现必须是线程安全的。
onEnd
BuildOutput 对象,包括输出文件和任何构建信息。
index.ts
Promise。在所有 onEnd() 回调执行完毕之前,Bun.build() 返回的 promise 不会解析。
index.ts