LmCast :: Stay tuned in

The JavaScript Midlife Crisis

Recorded: Sept. 22, 2026, 9:08 p.m.

Original Summarized

The JavaScript midlife crisis | Maroun BaydounMaroun Baydoun/BlogThe JavaScript midlife crisisSeptember 22, 2026Thirty years in, the JavaScript ecosystem would like to see other languages. They're younger, leaner and faster. What could possibly go wrong?Holding on to the crown?You could improve it, hide it, compile to it or complain about it. You just couldn't get rid of it.A while back, I made a half-observation, half-joke on LinkedIn.

The great JavaScript toolchain rewrite barged in. The older tools that helped cement the language's place in our stacks became uncool, if not suspicious. Their sluggish performance took the blame for slowing down millions of lines of code on their way to production. It's increasingly difficult to keep track of the cool kids on the block. Their names might not be catchy, but their promise is captivating: speed, and a lot of it.
It's a strange time to be a JavaScript developer. The language has never been more ubiquitous, yet it seems to be losing ground in its own backyard. The tools are faster, the setup easier, the abstractions thicker. We write, configure and wait less. We bundle, ship and hotfix more. What happens between our code and the end product becomes easier to ignore.
The benchmarks are all beaming green. The line charts are trending up, down, or sideways—whichever direction means fewer calls at 3 AM. So why am I here to ruin the party?
The language that wouldn't die
For a language (in)famously written in ten days, JavaScript managed to achieve the unthinkable. It escaped its birthplace, the browser, and started swallowing everything around it. The reaction was predictable: Who in their right mind would write their server and tools in JavaScript? It turned out, many many many would. JavaScript made it onto phones, gaming consoles, microcontrollers and your fridge. If it understands bits, it can run JavaScript.
Despite its popularity, JavaScript never had it easy. Not long after its inception, attempts to fix, or rather replace it altogether, were already in motion. Microsoft endowed Internet Explorer with VBScript and JScript, their own JavaScript flavour—not to be confused with J-Pop and JRPGs. In the 90s, everything sounded cooler if it started with J. Macromedia, and later Adobe, littered the internet with Flash intros and games powered by ActionScript. Google bet on Dart for the future of Chrome before relegating it to Flutter.
Projects such as CoffeeScript added some syntactic sugar to the JavaScript cup. When we weren't trying to replace JavaScript, we were busy patching it from the outside. jQuery unified a web platform whose browsers were barely on speaking terms. Lodash filled glaring gaps in the language's arrays and objects. Moment.js made dates somebody else's problem.
JavaScript wasn't sitting still while everyone plotted its demise, either. Within its single thread, it was rather busy. Browser vendors, standards bodies and the community kept pushing the language forward. ECMAScript releases brought long awaited language features. TC39 kept the proposals coming, and browsers slowly learned to agree on what JavaScript was supposed to do. Over time, its standard library became less embarrassingly sparse.
Then came TypeScript, and JavaScript's head was finally on a silver platter. Or so it seemed. TypeScript succeeded where the others failed by accepting one inconvenient truth: JavaScript wasn't going anywhere.
You could improve it, hide it, compile to it or complain about it. You just couldn't get rid of it.
The superpower we're giving away
One language to rule them all is both a blessing and a curse. We spent decades talking about the curse. Somewhere along the way, we forgot about the blessing.
As JavaScript continued to spread, it started eating its own dog food. Node.js enabled a slew of tools to emerge and conquer the ecosystem. Linters, bundlers, formatters and test runners were speaking the same language as the code they linted, bundled, formatted and tested.
If, or rather when, something broke in that toolchain, the average JavaScript developer would be able to check the code. Maybe they'd understand the bug. If they'd had their eight hours of sleep, maybe they'd fix it. If they were feeling combative, maybe they'd submit a pull request. At the very least, they knew enough of the language to confidently blame the bug on the maintainers.
And that familiarity travelled surprisingly well. The same language followed developers from the browser to the server, and eventually almost everywhere in between. JavaScript accelerated the rise of full-stack engineers, or perhaps full-ecosystem engineers. Whether anyone can truly master both ends of the stack without achieving demigod status is a discussion for another day. But JavaScript made the transition considerably easier. Engineers could bring along their knowledge of the call stack, prototype-based inheritance and the unfortunate fact that typeof null === "object" to almost any project.
People built entire careers and businesses around this catch-all ecosystem. The fact that most of it was and continues to be open source and free certainly helps.
JavaScript won the browser wars, and several key battles elsewhere. Then Rust and friends showed up for the trophy and the commemorative photo.
In pursuit of milliseconds
Rust, Go and Zig are taking over increasingly large parts of the JavaScript toolchain. And there's an obvious reason for that.
They're fast. Really fast.

We're compiling JavaScript with Rust to produce JavaScript that runs inside an engine written mostly in C++.

Nobody wants to stare at a build process long enough to form an emotional attachment to the progress bar. But when the replacement for an already-fast tool advertises itself as ten times faster, I start wondering what we're supposed to do with all those precious milliseconds it just handed us back.
Take an extra sip of coffee?
More importantly, what did we trade for that speed?
Rewrite a bundler in Rust and you haven't only made it faster. You've also shrunk the pool of JavaScript developers who can maintain it. The new tool still looks like a duck and quacks like a duck, but it's a different beast altogether. Its internals retreat behind a black box that fewer people hold the keys to. The source may still be open, but the door to contributions is closing.
Maybe that's a perfectly reasonable trade-off. But it is a trade-off. And we don't seem particularly interested in that side of the benchmark.
Not everything that shines is gold
Sometimes it's rusty.
Software engineering has always suffered from a particularly acute case of shiny object syndrome. Languages have their moment. Frameworks become fashionable. A few successful projects establish a pattern, companies invest in it, conference talks follow, laptop stickers get handed out and suddenly a technical decision becomes the main selling point.
"Written in Rust" starts sounding less like an implementation detail and more like a feature.
Success breeds imitation. One tool gets rewritten and becomes dramatically faster. Another follows, and another. Peer pressure mounts. Soon enough, being written in JavaScript starts to look less like the obvious choice for JavaScript tooling and more like a losing bet.

We're laying increasingly faster tracks for a steam train that likes to take its time.

None of this means those compiled languages are the wrong tools for the job. Quite often, they are exactly the right ones. But there's a difference between the right tool for this job and the right tool for every job that looks vaguely similar to whatever the competition is doing.
Once the shiny new tool also happens to top the benchmarks, resisting it becomes considerably harder. Speed provides the technical argument. Trendiness takes care of the rest.
Destination unknown
Our pursuit of faster JavaScript has taken us to a rather peculiar place.
We're compiling JavaScript with Rust to produce JavaScript that runs inside an engine written mostly in C++.
Perhaps that's the natural evolution of mature ecosystems, and JavaScript doesn't need to swallow the entire stack to remain relevant. Languages can coexist and still thrive. The web was built on at least three of them, before many more joined in.
Taken individually, every step makes perfect sense. Taken together, they point somewhere more interesting. We're putting a substantial amount of engineering into optimising everything around JavaScript while JavaScript itself remains the destination. We're laying increasingly faster tracks for a steam train that likes to take its time.
The thing about speed is that it doesn't always guarantee a smooth journey when the train itself isn't designed to keep up. Sooner or later, faster tracks will make less and less of an impact. And someone, much smarter than me, will have to ask the difficult question: how far can we go before rebuilding the web from the ground up starts looking like the saner option?You might also enjoyThe outstanding engineer who wanted to become a mediocre managerWhy do so many outstanding software engineers become mediocre managers? A reflection on promotions, ambition, and why climbing the career ladder doesn't always mean moving up.Don't start with ReactLearning technologies that the market is looking for is the logical thing to do. But should you start with React?Hi, I’m Maroun.I’m a Senior Software Engineer in Berlin. I build for the web, write things down, and give curious ideas their own URL.Let’s connect on LinkedIn or GitHub.ProjectsOpen sourceGithubLinkedinInstagramSubstack

The JavaScript ecosystem is currently undergoing a perceived midlife crisis, driven by the emergence of newer languages that promise greater speed and efficiency. While the language remains ubiquitous, there is a tension between its dominance and the rapid evolution of tooling and performance in the surrounding environment. This dynamic is characterized by a shift where modern tools offer faster execution and simpler setups, leading to a focus on bundling, shipping, and hotfixing, which can sometimes overshadow the core development process.

Despite these shifts, JavaScript has demonstrated remarkable resilience. It successfully expanded beyond its origin in the browser to permeate various domains, including phones, gaming consoles, and microcontrollers, indicating a broad applicability beyond its original context. Throughout its history, attempts to replace or retrofit JavaScript were countered by continuous evolution; projects like CoffeeScript, jQuery, and Lodash acted as external patches, while the language itself continued to advance through ECMAScript releases and collaborative efforts by standards bodies, ensuring its ongoing development. The eventual acceptance of TypeScript demonstrated that JavaScript was not destined for obsolescence, establishing a platform where developers could improve the language rather than abandoning it.

The unique power of the JavaScript ecosystem lies in the development of related tools, which have created a self-reinforcing system. Node.js enabled the proliferation of linters, bundlers, formatters, and test runners, all speaking the same language as the code they manage. This familiarity allows developers to trace bugs, understand the context of errors, and contribute effectively, fostering a strong sense of shared knowledge. This familiarity facilitates the movement of developers across the stack, accelerating the rise of full-stack and full-ecosystem engineers by enabling them to carry over conceptual knowledge from one domain to another.

The pursuit of raw speed is now driving significant changes, with languages like Rust, Go, and Zig entering the JavaScript toolchain. This pursuit stems from a desire for performance, and developers are compiling JavaScript using these faster systems. However, this pursuit introduces a critical trade-off: increased speed often comes at the cost of reduced maintainability and a shrinking pool of developers capable of maintaining these sophisticated tools. Replacing established tools with faster alternatives can create opaque systems where the internals are hidden behind a black box, potentially limiting community contributions despite the availability of source code.

Furthermore, the ecosystem is susceptible to the phenomenon of shiny object syndrome, where success breeds imitation. As new, faster tools gain prominence, there is pressure to adopt them, potentially leading to a cycle where the perceived reality of the choice dictates technical decisions rather than pure necessity. This pursuit of speed risks creating faster tracks for a process that is inherently designed to move at a measured pace. The central challenge moving forward is determining whether optimization around the existing JavaScript structure is the correct path, or if the system must undergo a fundamental rewrite. Ultimately, the trend suggests that the coexistence of multiple languages, each optimized for specific tasks, may represent a more sustainable evolution for the web than attempting for one language to subsume the entire stack.