Node.js 26 hit Active LTS on October 28, codename "Lithium." Two weeks later, it needed a security patch — 16 CVEs, seven of them HIGH severity, most exploitable over the network with no authentication required. That pairing tells you everything about where the ecosystem stands right now. The good news is that upgrading is straightforward. The bad news is that a few things will break if you don’t check for them first.
Patch to 26.13.1 Before You Do Anything Else
The November 11 security release (26.13.1) fixed critical flaws in Node’s HTTP/2 and TLS layers. These are not theoretical issues. CVE-2026-123863 crashes an HTTP/2 server with a single crafted request — no authentication, no session required. CVE-2026-123864 can leak TLS private keys. CVE-2026-126051 remotely crashes TLS servers using SNI callbacks.
This is not Node 26-specific. The same patch covers Node 24 (24.22.3) and Node 22 (22.23.5). If you’re on any supported LTS line and haven’t applied this, you have an open window right now. The official release notes list all 16 CVEs with severity ratings.
The Lifecycle Squeeze Is Real
What happened in late October is worth understanding clearly. On October 20, Node 24 moved from Active LTS to Maintenance. On October 28, Node 26 became Active LTS. Within eight days, the ecosystem shifted — the version most teams are running (24) is now in patch-only mode, while the new recommendation is Lithium.
“Maintenance” does not mean abandoned. It means security patches only — no new features, no non-critical bug fixes. Here is where things stand:
- Node 20: Already EOL as of April 2026. No patches at all.
- Node 22: Maintenance LTS, EOL April 30, 2027. Five months of security-only patches left.
- Node 24: Maintenance LTS, EOL April 30, 2028. Supported but frozen.
- Node 26: Active LTS, supported through April 30, 2029.
If you’re on Node 22, the clock is running. If you’re on Node 20 in production, something has gone wrong and needs fixing today.
What Node 26 Actually Gives You
The headline feature is Temporal — the modern date API that JavaScript has needed for twenty years. It’s enabled by default in Node 26, no flags required. The core value: immutable, timezone-aware date types that do math correctly.
// Date was always broken for month arithmetic
const d = Temporal.PlainDate.from('2026-01-31');
d.add({ months: 1 }).toString(); // '2026-02-28' — not '2026-03-03'
Temporal also distinguishes between “one day later” and “24 hours later” across daylight saving transitions — a source of real production bugs with the old Date object. You don’t need to rewrite existing code; Temporal is additive.
V8 14.6 brings Iterator helpers — iterator.map(), iterator.filter(), iterator.take(), and Iterator.concat() — letting you chain lazy operations without materializing intermediate arrays. JSON parsing is up to 12% faster on large payloads. Undici 8 (the HTTP client behind Node’s built-in fetch()) reduces keep-alive overhead, which matters for services that make many outbound API calls.
What Actually Breaks
Three things. Know them before you upgrade.
TypeScript Enums
This is the one that bites teams who thought “native TypeScript support” meant TypeScript was fully supported. It doesn’t. Node 26 removed --experimental-transform-types entirely — no deprecation warning, just gone. What remains is type stripping: annotations are removed, but enums, namespaces, and parameter properties are not compiled. If you try to run a file with a TypeScript enum natively in Node 26, you get ERR_UNSUPPORTED_TYPESCRIPT_SYNTAX before a single line of your code executes.
The fix is straightforward — replace enums with const objects:
// Before — breaks in Node 26 native mode
enum Status { Active = 'active', Inactive = 'inactive' }
// After — works with type stripping
const Status = { Active: 'active', Inactive: 'inactive' } as const;
type Status = typeof Status[keyof typeof Status];
If your project uses enums heavily, it’s faster to keep a build step (tsc or swc) than to refactor everything. That’s a legitimate choice.
Legacy Stream Modules
The undocumented _stream_readable, _stream_writable, _stream_duplex, _stream_transform, _stream_passthrough, and _stream_wrap modules are removed (DEP0193). They’ve been deprecated since Node 18, but old dependencies still reference them. Run grep -r '_stream_' ./node_modules --include="*.js" -l before upgrading to find transitive issues. The fix is const { Readable } = require('node:stream').
writeHeader()
http.Server.prototype.writeHeader() is removed. It was a typo alias for writeHead() that survived for years. If you’re calling res.writeHeader() anywhere, rename it to res.writeHead().
The Upgrade Decision by Version
The recommended approach is to install Node 26 alongside your current version using fnm or Volta (not over it), add it to your CI matrix for one sprint, then switch production once tests pass. Rolling back is a one-command operation with either tool.
Your current version determines the urgency:
- On Node 26.13.0: Patch to 26.13.1 today.
- On Node 24: Patch to 24.22.3, plan the Node 26 migration for Q1 2027.
- On Node 22: Patch to 22.23.5, treat the Node 26 upgrade as a priority before EOL in April 2027.
- On Node 20 or older: Treat this as an emergency, not a roadmap item.
Temporal alone is not a compelling reason to rush from a stable Node 24 production environment. The security patch is. Apply it now on whatever version you’re running, then plan the LTS migration with the sprint buffer you need.

