Tech debt used to be a backlog item. Now it’s a security question.
In August, a maintainer’s GitHub account for keyv, a caching library sitting quietly inside hundreds of thousands of projects, got compromised. Attackers pushed a malicious install script into it and eight related packages. Within hours the worm had spread to over 400 packages downstream, harvesting cloud and CI credentials from anyone who installed the wrong version that week.
It was the fourth major software supply chain attack on the JavaScript ecosystem this year. In March, axios, used by roughly 100 million projects a week, shipped a version with a remote access trojan baked in, after a maintainer account was hijacked. In June, attackers pushed malicious code into 32 packages under Red Hat’s own npm namespace, bypassing code review entirely. In July, four AsyncAPI release pipelines were compromised to publish trojanised packages. Four incidents, four different entry points, one pattern:
Attackers are going after the dependency, not the target.
That’s the part worth sitting with. None of the companies caught up in these incidents got hit directly. Their code was fine. Something they’d installed wasn’t.
Why unmanaged tech debt is a security risk
If you don’t know what’s sitting in your dependency tree, which versions, how deep, how old, you can’t answer a simple question fast: are we exposed? Teams with tidy lockfiles and a current picture of their dependencies can check that in an afternoon. Teams without one find out days later, usually from someone else’s incident report.
That gap is tech debt, plain and simple. It’s the kind that decides how fast you can move when it actually matters, and it’s easy to miss because it doesn’t show up as slow builds or an awkward upgrade path. A codebase where node_modules hasn’t been properly audited since a framework migration two years ago, where nobody’s quite sure why three different versions of the same utility library are installed, where the lockfile gets updated in a rush before a release and never looked at again: that’s a codebase that turns a ten-minute check into a multi-day scramble.
And the scramble is getting more frequent. Security researchers tracking the registry have watched the pace of these compromises accelerate through 2026, with campaigns now run by organised groups rather than opportunists chancing a typosquat. The registry itself hasn’t got any smaller either, and npm now hosts well over three million packages. A handful of foundational libraries carry the weight of most of the JavaScript ecosystem on their shoulders. One compromised maintainer account, and the blast radius runs to hundreds of downstream projects before anyone’s finished their coffee.
What actually reduces your software supply chain attack exposure
Pin your versions and gate new releases. CISA’s guidance after the axios compromise recommended setting a minimum release age in .npmrc: refuse to install anything published in the last week. It’s a small setting that buys real time, since most compromises get caught and pulled within days.
Know what’s actually in your tree, including the nested dependencies, not just the direct ones. A supply chain attack rarely hits the package you chose. It usually hits something three levels down that you inherited.
Treat dependency updates as current work, not backlog. Dependabot and Renovate PRs that sit open for months aren’t harmless. They’re the gap between “we checked this morning” and “we’re still working out what we’re running.”
None of this is new advice. What’s changed is the cost of ignoring it. A messy dependency tree used to mean slower builds and awkward upgrades. Now it means you can’t answer the one question that matters when the next keyv happens.
Debt doesn’t announce itself when it’s due. It just shows up as the thing that was too slow to check.

This article was written by Ed Bennett, Frontend Developer at JH.
Back before React was even a thing, Ed was messing about in Macromedia Dreamweaver, teaching himself to code long before it was a career. A decade of that has been professional, at JH for five years of it. What’s stayed constant is the appetite for problem solving and getting into the technical weeds, more the how-it’s-built side than the how-it-looks side. He’s picked up a full stack range of skills along the way rather than sticking with what he already knew. Away from the screen, he’s usually gaming or with family, sometimes both.
