The three supply-chain compromises that hit npm between March and May 2026 share a trajectory most coverage missed. They escalated from a general-purpose credential-theft RAT to attacks that explicitly targeted AI coding assistants, harvesting API keys, MCP server configs, and credential stores from development tooling. The attackers understood something the industry was slow to admit: an AI assistant’s local config file is now a privileged identity with repository write access.
The Axios Compromise: A Human Was the Exploit
On March 31, 2026, malicious versions of Axios (1.14.1 and 0.30.4) appeared on npm carrying a phantom dependency on plain-crypto-js@4.2.1, which deployed a cross-platform RAT targeting macOS, Windows, and Linux. The packages sat on the registry for 174 minutes before removal.
The initial access vector was social engineering, not a software vulnerability. Microsoft Threat Intelligence attributed the attack to Sapphire Sleet, a North Korean state actor. According to softscheck’s reconstruction, the attacker gained access to the lead maintainer’s PC through a targeted social engineering campaign and RAT malware, which yielded npm publish credentials.
From Axios to Bitwarden to TanStack: Three Attacks, Two Actors, One Target Surface
The Axios compromise was Sapphire Sleet’s work. The two that followed were a different threat group, TeamPCP, but the target surface was the same: developer tooling with high-privilege access to source code, secrets, and CI systems.
In April 2026, TeamPCP compromised the Bitwarden CLI npm package. TeamPCP is also responsible for compromising Aqua Security’s Trivy scanner (March 2026) and the checkmarx/ast-github-action, part of a series of campaigns against developer-security tooling. The Bitwarden payload harvested credentials and configuration files from AI coding assistants. The same group’s Mini Shai-Hulud wave on April 29, 2026, established what Snyk describes as the first documented AI coding agent persistence, targeting .claude/settings.json in the SAP and Intercom ecosystems.
Less than three weeks later, on May 11, 2026, 84 malicious npm artifacts were published across 42 @tanstack/* packages after attacker-controlled code hijacked the CI runner mid-workflow. The worm propagated to Mistral AI, UiPath, and dozens of other maintainers, ultimately producing 373 malicious versions across 169 packages using the Session P2P protocol for command-and-control, per Snyk’s analysis. The full campaign affected over 170 npm packages and 2 PyPI packages.
AI Coding Assistants Are Now a Supply-Chain Target
The TeamPCP campaigns didn’t just steal generic secrets. They specifically harvested AI-assistant configuration files and established persistence in agent config paths. The April 29 Mini Shai-Hulud wave was the first documented case of a supply-chain attack establishing persistence in an AI coding agent’s configuration (.claude/settings.json), per Snyk’s campaign timeline.
This is a direct consequence of how AI coding assistants work. Claude Code, Cursor, Codex CLI, and their peers read project-local and user-global config files that contain API keys, MCP server endpoints, and sometimes OAuth tokens. An AI assistant with write access to a repository is functionally a developer with write access. Compromise the assistant’s config and you compromise every repository it touches.
The TanStack campaign escalated further. Using stolen GitHub tokens, the attacker targeted AI assistant configuration in victim repositories. This is agent poisoning via supply chain: the malicious code doesn’t touch model weights or training data. It targets the configuration layer that tells the AI which tools to run and what permissions to grant.
Why Every Provenance Signal Failed
The npm ecosystem has accumulated several provenance mechanisms over the past few years. The 2026 attacks bypassed all of them.
OIDC trusted publishing. The TanStack attack hijacked the CI runner mid-workflow, then used the legitimate pipeline’s OIDC identity to publish malicious packages that appeared to come from legitimate CI, per Snyk’s analysis. Trusted publishing verifies that a publish action originated from a specific repository’s CI pipeline, not that the CI pipeline itself was clean.
SLSA Build Level 3 provenance. The malicious TanStack packages carried valid SLSA Build Level 3 provenance attestations, the first documented case of malicious npm packages with legitimate SLSA provenance. SLSA verifies the build process, not the build input. Hijack the CI runner and SLSA will attest to the tainted output.
Maintainer trust. The Axios compromise demonstrated that maintainer trust is a single point of failure. A weeks-long social-engineering campaign against one person yielded publish access to a package with tens of millions of weekly downloads. Two-factor authentication does not help when the maintainer’s development machine itself is compromised.
Each mechanism was designed to solve a specific link in the chain. The 2026 attacks compromised the links those mechanisms didn’t cover: the human operator (Axios), the developer tooling chain (Bitwarden), and the CI runner (TanStack).
What Actually Stopped the Attacks: The Boring Controls
None of the three compromises were stopped by provenance attestations, trusted publishing, or maintainer identity verification. They were stopped, or avoided entirely, by controls that have been standard advice for years.
Lockfiles. Teams that ran npm ci against a committed lockfile did not pull the malicious Axios versions, because npm ci installs exactly what the lockfile specifies and nothing else. Floating version ranges like ^1.14.0 resolved to whatever was latest at install time, including a release published minutes earlier. According to softscheck’s analysis, the average production Node.js application is approximately 3% first-party code and 97% open-source dependencies, often hundreds of packages deep. A lockfile pins every one of them.
ignore-scripts=true. All three attacks relied on npm lifecycle scripts (preinstall, postinstall) executing with full user privileges and no sandbox. Setting ignore-scripts=true in .npmrc prevents these hooks from running, which would have neutralized the payload delivery mechanism in all three cases, per softscheck’s analysis.
Cooldown policies. The Axios malicious versions were live for 174 minutes, per Microsoft’s advisory. Organizations with automated dependency update pipelines configured to delay adoption, such as Renovate’s minimum release age of 24 hours, would have aged past the malicious window before the update was even proposed.
What an AI Shop’s Dev-Tooling Audit Should Look Like Now
The Bitwarden and TanStack attacks established that AI coding assistants are not just users of the supply chain. They are targets within it. An AI shop’s dev-tooling audit needs to treat assistant configuration files, API key stores, and MCP server endpoints with the same access controls as production secrets.
Inventory AI assistant config paths. Know where AI assistant configuration directories (.claude/, .cursor/, and equivalent paths) live on developer machines. These files are the new ~/.ssh/. Treat them accordingly.
Restrict AI assistant token scope. The tokens stored in AI assistant config files should carry the minimum repository access required for the task. A Claude Code session with write access to every repository in the org is one config-file compromise away from a supply-chain breach.
Audit npm lifecycle scripts at install time. Set ignore-scripts=true in every development environment and CI pipeline. If a package requires lifecycle scripts to function, evaluate whether that package belongs in your dependency tree at all.
Pin and lock everything. Use npm ci exclusively. Commit lockfiles. Ban floating version ranges in direct dependencies and audit transitive dependencies for unpinned ranges.
Add a release-age gate. Configure Renovate, Dependabot, or equivalent tools to wait at least 24 hours before proposing dependency updates. The Axios compromise was live for under three hours. A cooldown policy is the cheapest defense against a short-window malicious publish.
Run SBOM diffs on every dependency update. The phantom dependency in the Axios attack (plain-crypto-js@4.2.1) would have been visible in a software bill of materials diff. Automated SBOM generation and comparison on every lockfile change catches additions that should not be there.
The 2026 supply-chain wave did not introduce a new vulnerability class. It exploited an existing one, npm’s permissive lifecycle-script execution model, and aimed it at a new high-value target: AI coding assistants holding repository write access and API keys. The defenses that work are the same ones that have always worked. The difference is that the stakes are higher, because the credentials living in developer tooling are no longer just npm publish tokens.
Frequently Asked Questions
How did the Axios RAT cover its tracks after execution?
The payload deleted its loader (setup.js), removed the triggering package.json, and renamed a clean stub (package.md to package.json) so that inspecting node_modules afterward revealed no install hook. On Windows, persistence used a registry run key at HKCU:\Software\Microsoft\Windows\CurrentVersion\Run\MicrosoftUpdate, which survives reboots and user logouts.
Would using Bun instead of npm have prevented these attacks?
Bun’s package manager ignores npm lifecycle scripts by default, which would have neutralized the payload delivery in all three incidents. Every attack depended on postinstall or preinstall hooks executing with full user privileges. Switching runtimes removes that execution vector, though it does nothing against the social-engineering or CI-hijack stages that preceded the payload.
What specific files did the Bitwarden payload steal from AI assistants?
The Bitwarden CLI payload harvested ~/.claude.json, ~/.claude/mcp.json, and ~/.kiro/settings/mcp.json, among other assistant config paths. It persisted via a 3.5 KB heredoc appended to ~/.bashrc and ~/.zshrc, so a fresh credential stealer fired on every new shell session until those lines were found and removed.
What credential stores did the TanStack payload target beyond npm tokens?
The payload swept GitHub Actions secrets, AWS credentials, HashiCorp Vault tokens, and Kubernetes service-account keys. Using stolen GitHub tokens, it also committed poisoned .claude/settings.json and .vscode/tasks.json into victim repos via GitHub’s GraphQL API, so the agent poisoning survived fresh clones by other developers.
How did the attacker actually compromise the Axios maintainer?
The Sapphire Sleet operator spent weeks building rapport on Slack while posing as a startup co-founder, then asked the maintainer to run a binary during a Microsoft Teams call. That binary installed the RAT that yielded npm publish credentials. Two-factor authentication on the npm account was irrelevant because the attacker already controlled the machine where the authenticated session lived.