Node earned its place. For fifteen years it was the obvious answer, and being obvious was most of the value. You reached for it without thinking because everyone else had, and that shared default was worth more than any single feature.
That’s exactly the thing that expired. The default got beaten on the merits, and once that happens, “everyone uses it” stops being a reason and starts being inertia.
The benchmark nobody on the Node side wants to quote
In February 2026, RepoFlow ran the same microbenchmark suite across the latest of each runtime: Node 25, Deno 2.6, Bun 1.3, all on an Apple M4. Fourteen tests, identical code, same machine.
Bun led eight. Deno took five. Node won one.
One. A SHA-256 hash on a small buffer. That’s the headline the “Node is still fine” crowd has to stand on: it hashes a kilobyte slightly faster than the thing that beat it everywhere that pays your bills.
Because look at where Bun won. Server throughput. Large JSON parsing. The HTTP path. The exact operations a real backend does ten thousand times a second while a request waits. Bun didn’t edge those out on a technicality, it stood out most on precisely the work you deploy a runtime to do.
Deno is genuinely fast too, mostly on async scheduling, and I’m not here to talk you out of it. But this is a coronation, not a committee. Bun won the categories that map to money.
Here’s every test, not just the scoreboard:
Speed is the boring reason
Here’s the part that actually changes your day, and it has nothing to do with requests per second.
Node never came with anything. You bolt it together. A package manager that pretends to be three different lockfile formats. A bundler. A test runner you install and configure. A separate tool to run TypeScript, until very recently. A different incantation for every one of those, and a node_modules folder that weighs more than the project.
Bun is one binary. It installs packages, and it does it fast enough that you double-check the command actually ran. It runs your tests. It bundles. It runs TypeScript directly with no transpile step you have to think about. The thing you spent an afternoon wiring together in Node is a flag in Bun.
That consolidation is the real argument. The runtime being faster is a nice line on a chart. The toolchain collapsing into a single command you already know is the thing you feel on every commit.
”Really have to”
I said don’t use Node unless you really have to, and the unless is load-bearing. There are honest reasons.
Some native module hasn’t been tested against Bun and you can’t afford to find out in production. A platform target only ships a Node runtime. A compliance checkbox names Node specifically. A team that would mutiny if you changed the thing under them this quarter. Those are real. If one of them is true, stay, and don’t feel bad about it.
But notice what none of those reasons are. None of them is “Node is faster.” None is “Node is simpler.” None is “Bun isn’t ready.” The case for Node now is compatibility and politics, which are legitimate constraints and a very different thing from technical merit. You’re not choosing Node because it’s better. You’re choosing it because moving costs something this week.
The honest framing
Node isn’t dying. It’ll run a huge share of the internet for another decade, the same way old reliable things always do, long after they stop being the choice you’d make fresh.
But “it’ll keep working” was never the question. The question is what you reach for when nothing forces your hand. For most of the last fifteen years the answer was Node, and the answer was right. It isn’t anymore. The default lost on its own numbers, and the only thing keeping it the default is that defaults are slow to admit they’ve been beaten.
Bun won. Reach for it first. Reach for Node when something makes you, and let that be the rule instead of the reflex.