前言
在 JavaScript 后端运行时领域,速度一直是核心战场。近年来,Bun 以其宣称的“一体化”工具链和闪电般的启动速度异军突起,对老牌王者 Node.js 发起了强劲挑战。bun run 的迅捷,让许多开发者开始重新评估他们的工具选择。
然而,Node.js 并未止步。自 v22.0.0 起,它悄然引入了一个专为启动性能而生的秘密武器:node --run。这个内置于 Node.js 核心的命令,旨在以最精简、最直接的方式执行 package.json 中的脚本,宣称要为最常见的用例提供“顶级性能”。
这引发了我们的好奇:在真实的场景下,这位新秀的表现究竟如何?它与 bun run 及传统的 npm run 相比,孰优孰劣?
本文将通过一系列严谨的对比测试,揭开 node --run 的神秘面纱,用数据回答:在 2026 年的脚本启动性能竞赛中,谁才是真正的速度王者?
各位小伙伴请注意!本文将颠覆这个传统观念“bun 启动一定比 Node.js 更快”。
首先我们回顾下 Node.js 运行文件有三种方式:
- 直接启动
node foo.[jt]s🤼♂️bun foo.[jt]s - package.json 脚本运行
npm run foo🤼♂️bun run foo - 脚本
--run直接运行node --run fooAdded in: v22.0.0 🤼♂️bun --run foo
统计方法,我们模仿竞技比赛中,去掉一个最高分和一个最低分,可以避免“冷启动”等极端数据干扰,采取去掉最大和最小值然后取平均值,这样抗干扰性强、更公平。
第一轮:直接启动 JS 文件速度
分别启动两个 mjs 文件,一个空一个有 IO 输出。测试文件:
// empty.mjs
// io.mjs
console.log('hello world');
Node.js 🟢
分别执行 time node empty.js time node io.mjs 各自三次。
❯ time node empty.mjs:
node empty.mjs 0.00s user 0.17s system 78% cpu 0.217 total
node empty.mjs 0.00s user 0.17s system 84% cpu 0.203 total
node empty.mjs 0.00s user 0.16s system 69% cpu 0.225 total
无 io 平均耗时:。
❯ time node io.mjs:
node io.mjs 0.00s user 0.17s system 73% cpu 0.234 total
node io.mjs 0.00s user 0.17s system 72% cpu 0.236 total
node io.mjs 0.00s user 0.17s system 74% cpu 0.229 total
io 平均耗时:。
整体耗时:。
Bun 🍞
bun empty.mjs 0.04s user 0.17s system 56% cpu 0.375 total
bun empty.mjs 0.00s user 0.21s system 63% cpu 0.337 total
bun empty.mjs 0.03s user 0.23s system 70% cpu 0.371 total
bun io.mjs 0.05s user 0.17s system 63% cpu 0.338 total
bun io.mjs 0.00s user 0.20s system 56% cpu 0.351 total
bun io.mjs 0.03s user 0.20s system 62% cpu 0.369 total
整体:
这数据有点反常,1 bun 启动 io 文件速度反而快于空文件,2 其次得到本文第一个非常重要的结论:bun 对 js 文件启动速度反而劣于 Node.js(二者相差 100ms+)。
第二轮:直接启动 TS 文件速度
[!TIP] 注意:想要不加参数直接运行 TS,Node.js 版本需 v22.18.0。
分别启动两个 ts 文件,一个空一个有 IO 输出。测试文件:
# 文件内容一样
empty-ts.ts
io-ts.ts
Node.js 🟢
node empty-ts.ts 0.00s user 0.19s system 73% cpu 0.254 total
node empty-ts.ts 0.00s user 0.17s system 72% cpu 0.236 total
node empty-ts.ts 0.00s user 0.17s system 71% cpu 0.240 total
无 io 平均耗时:。
❯ time node io-ts.ts:
node io-ts.ts 0.00s user 0.17s system 64% cpu 0.263 total
node io-ts.ts 0.00s user 0.17s system 67% cpu 0.255 total
node io-ts.ts 0.00s user 0.17s system 67% cpu 0.254 total
io 平均耗时:。
整体耗时:。
[!TIP] 小结:Node.js 运行 ts 耗时比 js 增加 ~20ms,这在预期内因为先要 amacro ts 编译器即将所有类型用空格替代。
Bun 🍞
bun empty-ts.ts 0.04s user 0.21s system 69% cpu 0.372 total
bun empty-ts.ts 0.01s user 0.15s system 45% cpu 0.372 total
bun empty-ts.ts 0.06s user 0.17s system 56% cpu 0.402 total
无 io 平均耗时:。
bun io-ts.ts 0.01s user 0.25s system 64% cpu 0.405 total
bun io-ts.ts 0.00s user 0.21s system 55% cpu 0.388 total
bun io-ts.ts 0.09s user 0.23s system 74% cpu 0.429 total
io 平均耗时:。
整体耗时:。
[!TIP] 小结:Bun 运行 ts 耗时比 js 增加 ~20ms,预期内。
本文第二个结论:bun 执行 ts 文件启动速度劣于 Node.js(二者相差 )。
有读者可能会问是否是通过环境变量寻址 bun 耗时导致的。那我们直接跳过寻址:
❯ time /e/pnpm/bun io-ts.ts
/e/pnpm/bun io-ts.ts 0.00s user 0.21s system 55% cpu 0.384 total
/e/pnpm/bun io-ts.ts 0.00s user 0.23s system 67% cpu 0.341 total
/e/pnpm/bun io-ts.ts 0.06s user 0.17s system 56% cpu 0.407 total
直接寻址耗时 ,确实少于 ,但依然显著高于 Node.js 的 !所以
结论一
Bun 无论启动 JavaScript 还是 TypeScript 文件都要慢于 Node.js!
注意这里是启动而非运行。
第三轮:package.json 脚本启动
结论先行:执行 package.json 内的 scripts bun run 的启动速度快于 npm run。我们测试下。
npm v11.7.0
我们定义两个 script io 和不含 io 的:
{
"type": "module",
"scripts": {
"io": "echo \"hello world\"",
"empty": ""
}
}
npm run
❯ time command npm run io
[!TIP]
command npm是因为我在~/.zshrc内对 npm 做了同名 alias 需通过command找到原始命令。
> rsbuild-react-19@1.0.0 io
> io "hello world"
"hello world"
command npm run io 0.00s user 0.39s system 58% cpu 0.660 total
command npm run io 0.00s user 0.34s system 52% cpu 0.649 total
command npm run io 0.01s user 0.31s system 50% cpu 0.638 total
npm run io 耗时:。
去除 IO:❯ time command npm run empty
command npm run empty 0.05s user 0.32s system 60% cpu 0.610 total
command npm run empty 0.03s user 0.34s system 59% cpu 0.626 total
command npm run empty 0.00s user 0.33s system 53% cpu 0.611 total
纯启动耗时 。
整体耗时:npm run 启动需 。这也太慢了,代码啥都没干呢!
接下来试试 bun run。
bun run
❯ time bun run io:
bun run io 0.03s user 0.21s system 79% cpu 0.308 total
bun run io 0.06s user 0.21s system 78% cpu 0.347 total
bun run io 0.00s user 0.21s system 68% cpu 0.313 total
左右
❯ time bun run empty:
bun run empty 0.04s user 0.18s system 60% cpu 0.380 total
bun run empty 0.01s user 0.21s system 69% cpu 0.330 total
bun run empty 0.03s user 0.21s system 67% cpu 0.361 total
左右。第二个反常 io 反而更慢。
整体耗时 。结论 bun run 大概是 npm run 的两倍()性能。
突然想起 Node.js v22.0.0 支持 node --run 运行脚本,专为性能而生,看看它表现如何。
第四轮:package.json 脚本 `--run` 直接运行
先解释下 node --run,是的,它也可以执行 package.json 中的脚本,而且生来就是为性能考虑(不会执行 pre / post 钩子)。
它将从
package.json文件的"scripts"对象中运行指定的命令。如果提供的"command"不存在,则会列出可用的脚本。
node --run并不旨在完全匹配npm run或其他包管理器的运行命令的行为。Node.js 的实现有意更加精简,以便在最常见的用例中专注于顶级性能。其他运行实现中一些被有意排除的功能包括:
- 除了运行指定的脚本外,还会运行前置(
pre)或后置(post)脚本。- 定义特定于包管理器的环境变量。
node --run
❯ time node --run io:
node --run io 0.00s user 0.17s system 79% cpu 0.216 total
node --run io 0.00s user 0.16s system 81% cpu 0.192 total
node --run io 0.00s user 0.19s system 84% cpu 0.220 total
完美 🤩
❯ time node --run empty:
node --run empty 0.00s user 0.17s system 89% cpu 0.192 total
node --run empty 0.01s user 0.16s system 80% cpu 0.212 total
node --run empty 0.00s user 0.17s system 89% cpu 0.192 total
完美 🤩🤩
node --run 整体平均:,确实做了性能优化,三倍性能提升 🚀:npm run 616ms VS node --run 204ms
bun --run
bun --run empty 0.06s user 0.14s system 53% cpu 0.370 total
bun --run empty 0.05s user 0.21s system 75% cpu 0.347 total
bun --run empty 0.04s user 0.21s system 68% cpu 0.379 total
bun --run io 0.01s user 0.18s system 61% cpu 0.324 total
bun --run io 0.01s user 0.23s system 73% cpu 0.334 total
bun --run io 0.03s user 0.17s system 52% cpu 0.382 total
(io 反而速度快于空脚本 -_-||)
bun --run 整体耗时 ,反常三:bun --run 慢于 node --run 的
性能数据总结
文章从三个维度(直接启动文件、运行 package.json 脚本、使用 --run 命令)对比了 Node.js 和 Bun 的性能。
核心结论
- 直接启动文件:无论 TS or JS,Node.js 以显著优势胜出。
- 运行 package.json 脚本:Bun (
bun run) 击败 npm (npm run),但node --run凭借其精简设计击败bun run / npm run / bun --run。
至此本文颠覆了一个传统观念“bun 启动一定比 Node.js 更快”。
附录:详细数据
表格一:直接运行 JS/TS 文件性能对比 (单位:ms)
| 测试场景 | Node.js (v22.18.0) | Bun (v1.3.2) | 性能胜出方 |
|---|---|---|---|
| 启动空 JS 文件 | ~217 | ~371 | Node.js (快 ~41%) |
| 启动含 IO 的 JS 文件 | ~234 | ~351 | Node.js (快 ~33%) |
| JS 文件启动综合耗时 | ~225 | ~361 | Node.js 胜出 |
| 启动空 TS 文件 | ~240 | ~372 | Node.js (快 ~35%) |
| 启动含 IO 的 TS 文件 | ~255 | ~405 | Node.js (快 ~37%) |
| TS 文件启动综合耗时 | ~248 | ~389 | Node.js 胜出 |
结论一: 在直接启动文件(无论 JS 或 TS)的场景下,Node.js 🚀 性能显著优于 Bun,平均领先幅度在 35%-41% 左右。虽然有反直觉但是我的 Windows 下确实如此。
表格二:运行 package.json 脚本性能对比 (单位:ms)
| 执行方式 | 平均耗时 (含IO) | 平均耗时 (空脚本) | 综合平均耗时 | 性能排序 (由快到慢) |
|---|---|---|---|---|
node --run | ~216 ms | ~192 ms | ~204 ms | 🥇 第1名 |
bun run | ~313 ms | ~361 ms | ~337 ms | 🥈 第2名 |
bun --run | ~334 ms | ~370 ms | ~352 ms | 🥉 第3名 |
npm run | ~650 ms | ~616 ms | ~633 ms | 第4名 |
结论二:
node --run是绝对的性能冠军,速度是npm run的 3.1 倍,也比bun run快约 65% 。- Bun 相关命令性能接近:
bun run和bun --run性能在同一水平,都显著快于npm run(快约 88%)。 npm run垫底:传统 npm 脚本的启动开销最大,耗时最长。
对我们的启发
- Node.js vs. Bun 启动速度:在直接启动
.js或.ts文件时,Node.js 比 Bun 快约 40%-60% 。这是“一个非常重要的结论”。 - Package Script 运行速度:
bun run比npm run快约 2 倍。- 而黑马 🐎
node --run比npm run快约 3 倍!
node --run 的意义——包脚本运行的革新:node --run 无疑是本次测试的最大亮点,其速度非常接近直接运行 node foo.js 的速度,实现了近乎“裸奔”的脚本执行性能。它通过牺牲 npm 脚本的部分高级功能(如 pre/post 钩子、特定的环境变量),换来了 ~3 倍于 npm run 的速度提升,甚至超越了以速度见长的 bun run。对于追求极致构建、测试或启动速度,且不依赖这些高级特性的项目,node --run 提供了一个近乎完美的“性能模式”。
启发:如果你要直接执行文件请使用 Node.js,如果要执行 npm script 建议 99% 情况下用 node --run(无需运行 pre / post npm script 时)否则 bun run。
说明
测试环境 Windows 10、git bash、Node.js 🟢 v22.18.0、npm v11.7.0、bun 🍞 v1.3.2。
—— 完 🎉 最新文章请关注公众号 JavaScript与编程艺术 ——