bun build CLI 命令或 Bun.build() JavaScript API 使用 Bun 的原生打包器。
一览
- JS API:
await Bun.build({ entrypoints, outdir }) - CLI:
bun build <入口文件> --outdir ./out - 监视:
--watch实现增量重建 - 目标环境:
--target browser|bun|node - 格式:
--format esm|cjs|iife(cjs/iife 为实验性功能)
- JavaScript
- CLI
build.ts

为什么要打包?
打包器可以解决以下几个问题:- 减少 HTTP 请求。
node_modules中的单个包可能由数百个文件组成,而大型应用可能有几十个这样的依赖。分别通过 HTTP 请求加载这些文件会变得难以承受,因此打包器会将应用源代码转换为数量更少的、自包含的“包”,从而可以通过单个请求加载。 - 代码转换。 现代应用通常使用 TypeScript、JSX 和 CSS 模块等语言或工具构建,在浏览器使用这些内容之前,必须将其转换为普通的 JavaScript 和 CSS。打包器是配置这些转换的理想位置。
- 框架功能。 框架依赖打包器插件和代码转换来实现文件系统路由、客户端与服务器端代码共存(例如
getServerSideProps或 Remix loaders)以及服务器组件等常见模式。 - 全栈应用。 Bun 的打包器可以通过单个命令处理服务器端和客户端代码,从而实现经过优化的生产构建和单文件可执行程序。借助构建时 HTML 导入,你可以将整个应用——前端资源和后端服务器——打包为一个可部署单元。
Bun 打包器不用于替代
tsc 进行类型检查或生成类型声明。基本示例
构建你的第一个 bundle。你有以下两个文件,它们实现了一个客户端渲染的 React 应用。index.tsx 是应用的“入口点”:也就是打包器开始处理的文件。通常,这是一个会执行某些副作用的脚本,例如启动服务器,或者在本例中初始化一个 React 根节点。由于这些文件使用了 TypeScript 和 JSX,因此必须先进行打包,然后才能发送到浏览器。
要创建 bundle:
entrypoints 中指定的每个文件,Bun 都会生成一个新的 bundle,并将其写入 ./out 目录(该路径相对于当前工作目录解析)。运行构建命令后,文件系统如下所示:
文件系统
out/index.js 的内容大致如下:
out/index.js
监听模式
和运行时与测试器一样,打包器原生支持监听模式。terminal
支持的内容类型
与 Bun 运行时一样,打包器默认支持多种文件类型。下表列出了打包器的标准“加载器”。参见 加载器。资源文件
遇到无法识别的文件后缀时,打包器会将该文件视为外部资源。会将引用文件原封不动复制到outdir 目录,同时导入被替换为文件路径。
naming 和 publicPath。
有关文件加载器的更多信息,请参见加载器。
插件
插件可以覆盖或扩展本表中所述的行为。参见加载器。API
入口点
必填 一个与应用程序入口点对应的路径数组。Bun 会为每个入口点生成一个捆绑包。- JavaScript
- CLI
build.ts
文件
用于内存打包的文件路径到文件内容的映射:打包磁盘上不存在的虚拟文件,或覆盖磁盘上已有文件的内容。此选项仅适用于 JavaScript API。 文件内容可以是string、Blob、TypedArray 或 ArrayBuffer。
完全内存打包
只需在files 中提供所有源文件,即可在磁盘上没有任何文件的情况下打包代码:
build.ts
files 中时,当前工作目录被用作根目录。
覆盖磁盘文件
内存文件的优先级高于磁盘上的文件,因此你可以在保持代码库其余部分不变的同时覆盖特定文件:build.ts
混合磁盘与虚拟文件
磁盘文件可导入虚拟文件,虚拟文件也可导入磁盘文件:build.ts
outdir
写入输出文件的目录。- JavaScript
- CLI
build.ts
outdir,则不会将打包后的代码写入磁盘。打包后的文件会以 BuildArtifact 对象数组的形式返回。这些对象是带有额外属性的 Blob;请参阅输出。
build.ts
outdir 后,BuildArtifact 上的 path 属性就是写入文件的绝对路径。
target
指定目标执行环境。- JavaScript
- CLI
build.ts
browser
默认值。 用于在浏览器中运行的捆绑包。解析导入时,优先使用
"browser" 导出条件。
导入 node:events 或 node:path 等内置模块可以正常工作,但调用某些函数(例如 fs.readFile)则无法正常工作。bun
用于在 Bun 运行时中运行的捆绑包。在许多情况下,无需捆绑服务器端代码;你可以直接执行源代码而无需修改。不过,捆绑服务器代码可以缩短启动时间并提高运行性能。对于在构建时导入 HTML、并将服务器端和客户端代码捆绑在一起的全栈应用,应使用此目标。所有使用
target: "bun" 生成的捆绑包都会标记 // @bun 编译指令,告知 Bun 运行时无需在执行前重新转译文件。如果任何入口点包含 Bun shebang(#!/usr/bin/env bun),捆绑器会默认使用 target: "bun",而不是 "browser"。结合使用 target: "bun" 和 format: "cjs" 时,会添加 // @bun @bun-cjs 编译指令,且 CommonJS 包装函数不兼容 Node.js。node
用于在 Node.js 中运行的捆绑包。解析导入时,优先使用
"node" 导出条件。Bun 不会为 Bun 全局对象或内置的 bun:* 模块提供 polyfill。format
指定生成 bundle 的模块格式。 Bun 默认为"esm",并提供 "cjs" 和 "iife" 实验性支持。
格式: “esm” - ES 模块
默认格式。支持 ES 模块语法,包括顶层 await 和import.meta。
- JavaScript
- CLI
build.ts
format 设置为 "esm",并使用 <script type="module"> 标签加载 bundle。
格式: “cjs” - CommonJS
要构建 CommonJS 模块,请将format 设置为 "cjs"。选择 "cjs" 后,默认目标会从 "browser"(esm)更改为 "node"(cjs)。使用 format: "cjs"、target: "node" 转译的 CommonJS 模块可以同时在 Bun 和 Node.js 中运行(前提是所使用的 API 均受两者支持)。
- JavaScript
- CLI
build.ts
格式: “iife” - IIFE
待完善文档,支持 globalNames 后发布。jsx
配置 JSX 的编译方式。
Classic 运行时示例(使用 factory 和 fragment):
importSource):
splitting
是否启用代码拆分。- JavaScript
- CLI
build.ts
true 时,打包器会启用代码拆分。当多个入口点导入同一个文件或模块时,打包器可以将这部分共享代码拆分到一个单独的包中,这个包称为 chunk。请考虑以下文件:
- JavaScript
- CLI
build.ts
文件系统
chunk-2fce6291bf86559d.js 文件包含共享代码。为避免文件名冲突,默认情况下文件名中会包含内容哈希。可以使用 naming 自定义此设置。
插件
打包时应用的插件列表。build.ts
env
控制打包期间如何处理环境变量。在内部,此选项使用define 将环境变量注入 bundle;env 是用于指定注入哪些环境变量的简写。
env: “inline”
将process.env.FOO 替换为包含环境变量实际值的字符串字面量,内联进 bundle。
- JavaScript
- CLI
build.ts
input.js
output.js
env: “PUBLIC_*“(前缀)
内联匹配给定前缀的环境变量(即* 字符之前的部分),将 process.env.FOO 替换为实际的环境变量值。使用前缀可以内联公共值(例如面向公众的 URL 或客户端令牌),而不会将私有凭据注入输出 bundle。
- JavaScript
- CLI
build.ts
terminal
index.tsx
output.js
env: “disable”
完全禁用环境变量注入。sourcemap
指定生成哪种类型的 sourcemap。- JavaScript
- CLI
build.ts
关联的
*.js.map sourcemap 是一个包含等效 debugId 属性的 JSON 文件。
压缩
是否启用代码压缩,默认false。
启用所有压缩选项:
- JavaScript
- CLI
build.ts
- JavaScript
- CLI
build.ts
外部依赖
外部依赖列表,默认空数组[]。
- JavaScript
- CLI
build.ts
index.tsx
index.tsx 会生成一个包含整个 “zod” 包源代码的构建产物。若要保持导入语句原样,则将其标记为外部依赖:
- JavaScript
- CLI
build.ts
out/index.js
* 标记所有导入为外部:
- JavaScript
- CLI
build.ts
包
控制是否将包依赖项包含在构建包中。可能的值:bundle(默认)、external。Bun 将导入路径不以 ., .. 或 / 开头的任何导入视为包。
- JavaScript
- 命令行
build.ts
命名
自定义生成文件名。默认'./[dir]/[name].[ext]'。
- JavaScript
- CLI
build.ts
file system
file system
naming 字段用于自定义生成文件的名称和位置。它接受一个模板字符串,该字符串用于所有与入口点对应的捆绑文件,其中以下标记会被替换为相应的值:
[name]- 入口文件名(无扩展名)[ext]- 生成文件扩展名[hash]- 文件内容哈希值[dir]- 项目根目录相对路径到源文件父目录
组合这些标记以创建模板字符串。例如,要在生成的捆绑文件名中包含哈希值:
- JavaScript
- CLI
build.ts
file system
naming 字段提供字符串时,该字符串仅用于与入口点对应的捆绑文件。代码块和复制的资源名称不会受到影响。在 JavaScript API 中,可以为每种类型的生成文件指定单独的模板字符串。
- JavaScript
- CLI
build.ts
根目录
项目根目录。- JavaScript
- CLI
build.ts
文件系统
pages 目录中构建两个入口文件:
- JavaScript
- CLI
文件系统
pages 目录是入口文件的第一个公共祖先目录,因此它被视为项目根目录,所以生成的构建文件位于 out 目录的顶层;不存在 out/pages 目录。
通过指定 root 选项可以覆盖此行为:
- JavaScript
- CLI
root 为 . 时,生成的文件结构如下:
publicPath
添加到打包代码中所有导入路径前的前缀。 在许多情况下,生成的 bundle 不包含任何导入语句;打包的目标就是将所有代码合并到单个文件中。不过在少数情况下,生成的 bundle 会包含导入语句:- 资源导入 — 导入
*.svg等无法识别的文件类型时,打包器会交由文件加载器处理,文件加载器会将文件原样复制到outdir中。导入会被转换为一个变量。 - 外部模块 — 被标记为外部的文件和模块不会包含在 bundle 中,而是将导入语句保留在最终的 bundle 中。
- 代码分块。 启用
splitting后,打包器可能会生成单独的“chunk”文件,用于表示多个入口点之间共享的代码。
publicPath 会使用指定的值作为所有文件路径的前缀。
- JavaScript
- CLI
build.ts
out/index.js
定义
一个全局标识符映射,用于在构建时进行替换。此对象的键是标识符名称,值是会被内联的 JSON 字符串。- JavaScript
- CLI
build.ts
加载器
将文件扩展名映射到内置加载器名称的表。使用它自定义某些文件的加载方式。- JavaScript
- CLI
build.ts
横幅
添加到最终 bundle 中的横幅内容。它可以是 React 使用的"use client" 指令,也可以是许可证等注释块。
- JavaScript
- CLI
build.ts
页脚
添加到最终构建包的页脚。可以是许可证的注释块,也可以是一个有趣的彩蛋。- JavaScript
- CLI
build.ts
drop
从捆绑包中移除函数调用。例如,--drop=console 会移除所有对 console.log 的调用。被移除调用的参数也会被移除,即使这些参数具有副作用。移除 debugger 会移除所有 debugger 语句。
- JavaScript
- CLI
build.ts
功能
Enable compile-time feature flags for dead code elimination: conditionally include or exclude code paths at bundle time usingimport { feature } from "bun:bundle".
app.ts
- JavaScript
- CLI
build.ts
feature() 在打包时替换为布尔值,结合压缩,可剔除不可达分支:
输入
输出(启用 --feature PREMIUM --minify)
输出(不启用 --feature PREMIUM,启用 --minify)
feature()要求传入字符串字面量参数——不支持动态值bun:bundle导入会从输出中完全移除- 适用于
bun build、bun run和bun test - 可以启用多个标记:
--feature FLAG_A --feature FLAG_B - 如需类型安全,可扩展
Registry接口,将feature()限制为已知标记
- 平台差异代码(
feature("SERVER")vsfeature("CLIENT")) - 环境变量控制功能(
feature("DEVELOPMENT")) - 渐进式功能发布
- A/B 测试
- 付费版功能区分
feature() 可传任意字符串。想实现自动提示防错,可新建 env.d.ts 文件(或补充到已有 .d.ts)并声明扩展:
env.d.ts
tsconfig.json 中(例如 "include": ["src", "env.d.ts"])。现在,feature() 只接受这些标记,像 feature("TYPO") 这样的无效字符串会产生类型错误。
optimizeImports
跳过对桶文件(重新导出索引文件)中未使用子模块的解析。当你从大型库中仅导入少量具名导出时,通常打包器会解析桶文件重新导出的每个文件。使用optimizeImports 后,只会解析你使用的子模块。
build.ts
import { Button } from 'antd' 通常会解析 antd/index.js 重新导出的所有约 3000 个模块。使用 optimizeImports: ['antd'] 时,只会解析 Button 子模块。
这适用于纯桶文件——即每个具名导出都是重新导出的文件(export { X } from './x')。如果桶文件有任何本地导出(export const foo = ...),或者有任何导入者使用了 import *,则所有子模块都会被加载。
export * 重新导出的模块始终会被加载(不会延迟),以避免循环解析问题。只有未被任何导入者使用的具名重新导出(export { X } from './x')才会被延迟加载。
自动模式: 在 package.json 中带有 "sideEffects": false 的包会自动启用桶优化——无需配置 optimizeImports。对于没有该字段的包,可以使用 optimizeImports。
插件: Resolve 和 load 插件可与桶优化配合使用。延迟加载的子模块最终加载时,会经过插件管道。
元数据文件
生成结构化格式的构建元数据。元数据文件描述每个输入和输出文件,包括大小、导入和导出。可用于:- Bundle 分析:了解哪些内容影响 Bundle 大小
- 可视化:提供给 esbuild 的 Bundle 分析器 等工具
- 依赖跟踪:查看应用程序的完整导入图
- CI 集成:跟踪 Bundle 大小随时间的变化
- JavaScript
- CLI
build.ts
Markdown 元数据文件
使用--metafile-md 生成一个 Markdown 元数据文件,它对 LLM 友好,并且在终端中可读:
terminal
--metafile 和 --metafile-md 可同时使用:
terminal
metafile 选项格式
在 JavaScript API 中,metafile 支持以下几种形式:
build.ts
输出
Bun.build 返回一个 Promise<BuildOutput>,定义如下:
build.ts
outputs 数组包含构建生成的所有文件。每个 artifact 都实现了 Blob 接口。
build.ts
BuildArtifact 对象可以直接传给 new Response()。
build.ts
BuildArtifact 对象。
字节码
bytecode: boolean 选项会为任何 JavaScript/TypeScript 入口点生成字节码,这可以显著提升大型应用的启动速度。需要 "target": "bun" 以及匹配版本的 Bun。
- CommonJS:无论是否使用
compile: true都可以工作。会在每个入口点旁生成一个.jsc文件。 - ESM:需要
compile: true。字节码和模块元数据会嵌入独立可执行文件中。
format,字节码默认为 CommonJS。
- JavaScript
- CLI
build.ts
可执行文件
Bun 支持将 JavaScript/TypeScript 入口“编译”为独立可执行文件,其中包含 Bun 二进制文件。terminal
日志和错误
失败时,Bun.build 会返回一个被拒绝的、包含 AggregateError 的 Promise。将其记录到控制台可以美化打印错误列表,也可以通过 try/catch 代码块以编程方式读取。
build.ts
Bun.build 调用前使用顶层 await。
错误列表中每条均为 BuildMessage 或 ResolveMessage 实例(继承自 Error),含详细信息:
build.ts
logs 字段,包含打包警告和信息。
build.ts
参考
TypeScript 定义
CLI 用法
通用配置
boolean
设置
NODE_ENV=production 并启用压缩boolean
编译时使用字节码缓存
string
default:"browser"
打包的预期执行环境。可选
browser、bun 或 nodestring
传递自定义解析条件
string
default:"disable"
将环境变量内联到包中,形式为
process.env.$。要内联匹配某个前缀的变量,可以使用类似
FOO_PUBLIC_* 的通配符输出与文件处理
string
default:"dist"
输出目录(用于构建多个入口点时)
string
输出到指定文件
string
default:"none"
生成源码映射。可选
linked、inline、external 或 nonestring
在输出文件前添加标头(例如 React 服务器组件的
“use client”)在输出文件尾部添加注释(例如
// built with bun!)string
default:"esm"
输出包的模块格式。可选
esm、cjs 或 iife。当使用 —bytecode
时,默认值为 cjs。文件命名
string
default:"[dir]/[name].[ext]"
自定义入口点的文件名格式
string
default:"[name]-[hash].[ext]"
自定义代码块文件名格式
string
default:"[name]-[hash].[ext]"
自定义资源文件名格式
打包选项
string
打包多个入口点时使用的根目录
boolean
启用共享模块的代码分割
string
添加到打包代码中导入路径的前缀
string
从包中排除模块(支持通配符)。别名:
-estring
default:"bundle"
依赖处理方式:
external 或 bundleboolean
只进行转译,不打包
boolean
合并 CSS 文件以减少重复(仅当多个入口点引入 CSS时生效)
压缩与优化
boolean
default:"true"
重新输出死代码消除注释。在使用
—minify-whitespace 时禁用boolean
启用所有压缩选项
boolean
压缩语法并内联常量
boolean
压缩空白字符
boolean
压缩变量和函数标识符
boolean
压缩时保留原始的函数和类名称
开发功能
boolean
文件变化时自动重建
boolean
使用
—watch 时不清屏boolean
启用 React 快速刷新转换(用于开发测试)
boolean
在
.jsx/.tsx 文件上运行 React 编译器,自动对组件和 hooks 进行记忆化。输出模式由
—target 决定(browser → client,bun/node → ssr)。实验性功能。独立可执行文件
boolean
生成一个包含该包的独立 Bun 可执行文件
string
向独立可执行文件的
execArgv 前置参数Windows 可执行文件详情
boolean
运行编译后的 Windows 可执行文件时防止打开控制台窗口
string
设置 Windows 可执行文件图标
string
设置 Windows 可执行文件产品名称
string
设置 Windows 可执行文件公司名称
string
设置 Windows 可执行文件版本(例如
1.2.3.4)string
设置 Windows 可执行文件描述
string
设置 Windows 可执行文件版权声明
实验性功能及应用构建
boolean
(实验性) 使用 Bun Bake 构建生产环境的 Web 应用
boolean
(实验性) 启用 React 服务器组件
boolean
当设置了
—app 时,即使是静态构建也将所有服务器文件导出到磁盘boolean
当设置了
—app 时,禁用所有压缩