Bun:JS工具链的降维打击

Bun:JS工具链的降维打击

Node是标准,Deno是理想,Bun是效率。


一、赛道已经换了:为什么JSC赢了V8

Bun的碾压级速度不是魔法,是一个清晰的架构选择——用"长运行峰值吞吐"换"短任务极速启动"

V8(Node/Deno) JavaScriptCore(Bun)
设计目标 Chrome长时页面渲染 Safari快速打开标签页
优化方向 JIT预热后峰值吞吐 冷启动+首次执行速度
内存footprint 较大(~40MB基线) 较小(~18MB基线)
适配场景 长运行重型计算 I/O密集+短生命周期任务

这不是在比较V8和JSC谁"更好",而是指出:Node选错了优化目标。V8为Chrome的长时页面渲染而生,JIT偏重峰值吞吐。但服务端JS的典型负载是"起一个进程,做点I/O,然后死掉"——JIT预热的时间比干活的时间还长。Bun用JSC,是把优化目标从"跑久了好"扭转为"跑得快、死得干净",这恰好命中了Serverless时代的物理账本。

再用Zig写运行时——无GC拖累的底层内存管理,系统调用路径极短,冷启动压到毫秒级。加上Linux io_uring内核级异步I/O,不走libuv事件循环。

不是Bun比V8"更好",是Bun选了更适合JS服务端典型负载的引擎。一旦成本函数对了,选引擎就自然了。


二、为什么JS服务端负载长这样:三个产业结构变迁

JS服务端"短生命周期+I/O密集"的负载形态不是天然的,是三个历史力量共同塑造的:

2.1 计算的民主化——前端开发者涌入后端

他们用JS不是因为JS是最好的服务端语言,而是因为这是他们唯一会的语言。这决定了服务端JS的典型任务不是数值计算(那是Python/Julia的地盘),而是胶水逻辑——接请求、查数据库、拼JSON、返回响应。胶水逻辑天然是I/O密集的。

2.2 计算的碎片化——Serverless/微服务/边缘计算

模式 进程生命周期 计算特征
单体应用(2005) 天级 CPU可预热,JIT有时间优化
微服务(2015) 小时级 部分可预热,但容器调度频繁
Serverless(2020) 毫秒级 JIT预热时间 > 执行时间
边缘计算(2023) 毫秒级+冷启动频繁 每次请求可能都是冷启动

当进程从"天级"压缩到"毫秒级",V8的JIT优化窗口从"充裕"变成了"负数"——预热还没完成,进程已经死了。这不是V8的bug,而是时代变了。

2.3 计算的商品化——按调用计费

Serverless按ms计费,边缘计算按请求计费。在这个经济模型下,冷启动时间就是直接成本。Bun省100ms冷启动不是"快一点",是每次调用少付100ms的钱。百万级调用下,这就是账面上的数字。


三、裁判重定义:Bun不是在赢比赛,而是在换裁判

Bun真正的力量不在"更快",而在重新定义了什么叫"快"

裁判 Node表现 Bun表现 胜者
JIT预热后峰值吞吐 ✅ 强(V8老本行) ⚠️ 一般 Node
冷启动时间 ❌ 60-120ms ✅ 8-15ms Bun
基线内存占用 ❌ 40MB ✅ 18MB Bun
端到端成本(Serverless) ❌ 贵 ✅ 省 Bun

Node在旧裁判(JIT预热后峰值吞吐)下赢了,Bun在新裁判(端到端成本)下赢了。新裁判为什么取代旧裁判?因为产业结构变迁让新裁判更接近真实成本函数。

这和AlphaGo Zero的结构同构:

AlphaGo vs Zero Node vs Bun
旧裁判 模仿人类棋谱的准确度 JIT预热后峰值吞吐
新裁判 终局胜负 端到端成本
裁判切换的驱动力 自我对弈发现了更优策略 产业结构变迁改变了真实成本函数
旧方案的"口音" 人类棋谱偏见残留在权重中 V8的长运行优化偏执残留在架构中

但这不是零和博弈——JS运行时不是围棋。Node不会因为Bun的存在而消失,因为企业存量项目、CPU密集场景、LTS需求、C++原生模块生态都是Node的护城河。在开环世界中,多个裁判可以共存,不同场景需要不同的裁判。


四、快多少:数据说话

指标 Bun 1.3 Node.js 24 Deno 2.6 倍数
HTTP吞吐 ~110k req/s ~45k ~85k 2.4× vs Node
冷启动 8–15ms 60–120ms 40–60ms 10× vs Node
包安装(冷) ~1s ~20s ~17s 20× vs npm
包安装(热) ~0.3s ~8s ~0.8s 27× vs npm
TS执行 ~10ms ~150ms(需tsx) ~30ms 15× vs Node
SQLite 10k行插入 12ms 88ms 45ms 7× vs Node
基线内存 ~18MB ~40MB ~30MB 一半不到
大monorepo(1847依赖) 47s 28min 36×

冷启动10×差距对Serverless是真金白银——Lambda按ms计费,Bun每次调用省100ms,百万级调用就是显著成本差异。


五、All-in-One:DX的涌现

需求 Node生态 Bun
包管理 npm/pnpm/yarn bun install
打包 webpack/esbuild/rollup bun build
测试 jest/vitest bun test
TypeScript tsx/ts-node 原生支持 ✅
.env dotenv 原生读取 ✅
JSX 配置babel/tsx 原生支持 ✅
SQLite better-sqlite3 bun:sqlite
单文件分发 pkg/nexe bun build --compile

单独看每一项,都不是不可替代的。bun test可以换成jest,bun build可以换成esbuild。但当这一切内建在一个二进制里,而且零配置可用时,就发生了质变。

"Going back to Node feels like stepping back 5 years"——这是DX涌现的典型症状。无数小的、可判定的改进(启动快一点、安装快一点、原生支持TS),在某个临界点之后,集体跃迁到另一个不可判定的体验层级。你无法用一个benchmark证明"DX好10×",但迁移过的人都知道它真实存在。

构建管线从"拼装"变"原生",抹平了Webpack/esbuild/Jest的配置摩擦。


六、兼容策略:Drop-in Replacement,不颠覆

与Deno强推Web标准、自建生态不同,Bun优先实现Node.js API(fs, http, net, path等)和npm包兼容。

  • 98-99% npm兼容——bun run index.js基本直接替换node index.js
  • Express、Hono、Next.js(99%兼容,实验性)、Prisma、Zod都能跑
  • 不能用的5%:node-gyp编译的原生C++模块(bcrypt、sharp某些配置)、node:crypto边缘case

迁移成本极低,企业存量项目无痛接入,不破坏现有依赖树。


七、生产采纳证据

公司 用Bun做了什么
Anthropic Claude Code CLI用Bun单文件可执行
Midjourney 内置WebSocket服务器做生成通知
Vercel 2025年底原生支持Bun部署Next.js
Railway Serverless函数用Bun运行

八、何时选/不选

选Bun

  • Serverless/短生命周期任务(冷启动10×优势直接变钱)
  • CI/CD管线(1847依赖47s vs npm的28min)
  • CLI工具(单文件可执行分发)
  • 前端基建、快速原型
  • 追求极致DX的团队

谨慎选择

  • 重度依赖V8特有优化(特定N-API C++ Addon、复杂长时数值计算)——JSC的JIT路径与V8不同,CPU密集场景Bun接近甚至略输Node(React SSR 4,150 vs 4,200 ops/sec)
  • 强依赖Node最新实验性API
  • 需要LTS的企业(银行、医疗)——Bun没有长期支持策略
  • 需要安全模型——Deno默认拒绝一切权限,Bun没有权限控制
  • Windows为主的环境——Bun 1.x在Windows上兼容性和性能显著弱于macOS/Linux

九、技术史的一个模式

Bun的故事不是孤例。回顾历史,"裁判重定义"反复出现:

旧裁判 旧胜者 新裁判 新胜者 驱动力
单核峰值性能 C++ 并行吞吐 Java/C# 多核普及
手动内存管理效率 C 开发效率 Python/JS 开发者成本上升
JIT预热后峰值 Node(V8) 冷启动+端到端成本 Bun(JSC) Serverless兴起

每次裁判重定义的背后,都是成本结构的变迁——当某个成本维度从"可忽略"变成"占大头"时,优化方向就必须切换。

Python比C慢100倍,但开发者效率高10倍——当开发者成本 > 计算成本时,Python赢了。
Bun在CPU密集场景略输Node,但冷启动快10倍——当冷启动成本 > 峰值吞吐差异时,Bun赢了。

那成本结构为什么会变迁?因为抽象层次的迁移

每当一个行业把某一层的实现"做完了"——单核优化到了物理极限、手动内存管理的边际收益趋近于零——成本结构就自动转移到下一层未被满足的需求上:并行吞吐、开发效率、冷启动开销。这不是某个工具的功劳,而是技术演化的结构性必然:每一层的"做完了",就是下一层"赛道切换"的发令枪。

C++把单核性能做到了极致,于是成本重心转移到"如何利用多核"——Java/C#胜出。C把手动内存管理做到了极致,于是成本重心转移到"如何降低开发者心智负担"——Python/JS胜出。Node把服务端JS的长运行吞吐做到了可用,于是成本重心转移到"如何让短生命周期任务更便宜"——Bun胜出。

技术史的本质不是"更好的工具取代更差的工具",而是"更匹配当前成本结构的工具取代不再匹配的工具"——而成本结构本身,由抽象层次的迁移驱动。


十、一句话

Bun不是在Node的赛道上跑得更快,而是发现赛道已经换了。

产业结构变迁漂移了成本函数,成本函数的漂移淘汰了旧裁判,抽象层次的迁移让这一切成为必然——Bun只是这个结构中一个具体的、可验证的截面。


雨轩于听雨轩 🌧️🏠