大家好,我是何三,独立开发者。
上周 Hacker News 上有个事儿炸了:705 个点赞,532 条评论,全在吵一个话题——Bun 要抛弃 Zig,转投 Rust。
Bun 是什么?89k Star 的 JavaScript 运行时,之前一直是用 Zig 写的,跑得贼快。结果 Anthropic(就是搞 Claude 那家公司)把 Bun 收购之后,直接开了个分支叫 claude/phase-a-port,用 Claude AI 把核心代码从 Zig 往 Rust 翻译。
离谱吗?离谱。但更离谱的是:这件事背后暴露的,是 Rust 对 Zig 的一场全面"降维打击"。
说白了,这不是什么"语言之争"的键盘侠口水战,而是工程现实的残酷选择。
先搞清楚:Bun 为什么要跑路?
先说一下背景,免得有人没跟上。
Bun 最初选 Zig 是有道理的。Zig 的 C 互操作性极好,性能直逼 C,而且有 comptime(编译期执行)这种骚操作——能在编译阶段就算好很多东西。
但问题在于,Zig 实在太"嫩"了。
版本才 0.16,每 6 个月来一次 breaking change。今天能跑的代码,明天就给你编译报错。Bun 团队为了填这个坑,不得不自己 fork 了一个 Zig 分支,做了 4 倍更快的调试编译优化——但问题来了:这些优化回不去上游。
对,你没听错。你 fork 了别人的编译器自己改了 bug,但官方不接收你的代码。你只能自己维护这个分支。
你说这得有多疼?
我曾经 fork 过一个 npm 包改了一行代码,后面天天被 Dependabot 追着打补丁……那感觉,懂的都懂。
Rust 到底比 Zig 强在哪?来,上硬菜
说实话,我刚看到 Bun 转向 Rust 的第一反应也是:Zig 不是性能很强吗?有必要换吗?
但看完 PORTING.md 里的迁移指南和社区讨论,我服了。
1. 内存安全:Rust 的杀手锏
这是最核心的区别。直接上代码对比。
Zig 的写法(当前 Bun 的代码):
const c = @cImport(@cInclude("JavaScriptCore.h"));
pub fn evaluateScript(ctx: *c.JSContextRef, source: [*]const u8) callconv(.C) ?*c.JSValueRef {
// 显式调用,但没有任何指针生命周期保护
return c.JSEvaluateScript(ctx, source, null, null, 0, null);
}
Rust 的等价写法:
use crate::bindings::JavaScriptCore::{JSContextRef, JSValueRef, JSEvaluateScript};
#[no_mangle]
pub extern "C" fn evaluate_script(
ctx: *mut JSContextRef,
source: *const u8,
) -> *mut JSValueRef {
// 生命周期约束在编译期验证
// 空指针解引用在编译期捕获
// use-after-free 通过所有权语义消除
unsafe {
JSEvaluateScript(ctx, source, std::ptr::null(), std::ptr::null(), 0, std::ptr::null_mut())
}
}

看懂了吗?Zig 那一大堆用 @ 开头的魔法看着很酷——但它没有 borrow checker。返回一个指向栈内存的指针,在 Zig 里就是能跑。直到它在生产环境里炸了,你才发现是内存问题。
而 Rust 的 unsafe 块是显式、可审计的。出了事你知道在哪个框里找。
用大白话说就是:Zig 给了你一把没保险的枪,Rust 至少给枪上了个安全栓。
2. 生态成熟度:不是一个量级

这个表格一拉,差距就很直观了。Zig 的社区很有爱,但 Rust 的生态是拿真金白银砸出来的。
为什么 Cloudflare 用 Rust?为什么 AWS 用 Rust?为什么 Linux 内核都开始接纳 Rust?因为 Rust 的 "编译过了就能跑" 在企业级场景里太香了。
3. AI 政策冲突:一个被低估的原因
这事挺有意思的。
Zig 官方有一条严格的规定:不允许 AI 生成的代码贡献到项目中。Zig 作者 Andrew Kelley 对这事态度很硬。
但 Bun 现在归谁了?Anthropic——一家 AI 公司。
Anthropic 的整个开发工作流都是 AI 驱动的,你用 Claude 写代码、用 AI 做 Code Review、用 AI 来重构——然后你依赖的语言说"AI 写的代码不准用"?
这就像你开了一家电动车公司,结果供应商说"我们只卖汽油车"。不是谁对谁错的问题,是根本没法合作。
道理我都懂,但用 AI 把整个 runtime 从 Zig 翻译成 Rust……这个操作我确实没想到。只能说 Anthropic 是真的狠。
那 Bun 到底跑了吗?
欸,这里得冷静一下。
Bun 的核心开发者 Jarred 在 HN 上亲自回复了:
"整个帖子都在过度反应。这些代码很可能被全部丢掉。我们还没承诺重写,只是想看看一个 Rust 版本跑起来什么样。"
所以严格来说,Bun 还没有正式决定全面转向 Rust。
但这个分支本身就是一个信号。
Jarred 说他想看看两套代码放在一起对比的效果。当一个项目的核心开发者开始做这种对比的时候……你懂的。
如果你也想试试
Bun 的迁移分支是公开的,如果你好奇 Rust 版本的 Bun 长什么样:
git clone https://github.com/oven-sh/bun
cd bun
git checkout claude/phase-a-port
cat docs/PORTING.md
那个 PORTING.md 就是 Zig → Rust 的迁移指南,写得挺详细的。虽然代码还不一定能跑,但看看迁移思路也有启发。
如果你看完这篇对 Bun 开始感兴趣了,它依然是个好项目:
GitHub 地址: https://github.com/oven-sh/bun
目前还是 Zig 版本为主,日常开发完全没问题,跑得还是那么快。
觉得 Rust 和 Zig 之争有意思?我上次还整理过一篇关于 Tauri(用 Rust 写的桌面应用框架)的文章,戳→ 关注「何三笔记」,回复「Rust桌面」获取。
同类项目中,Deno 从一开始就是用 Rust 写的,如果你想看纯 Rust 实现的 JS 运行时,Deno 是个好参考。
说实话,这场 Zig vs Rust 的争论对普通开发者来说可能没什么影响。你该用 Bun 还是用 Bun,该写 JS 还是写 JS。
但如果你正面临语言选型,这个故事给了一个很明确的答案:生态成熟度 > 语言特性炫酷度。
Zig 的 comptime 确实性感,但 Rust 的 borrow checker 和 Cargo 才是真正让你晚上能睡得着觉的东西。
本文使用 MGO 编辑并发布
关注"何三笔记",回复"mgo" 免费下载使用