Mini Shai-Hulud Worm Compromises TanStack, Mistral AI, & More

The Emergence of a New Supply Chain Threat

A sophisticated attack campaign has recently sent shockwaves through the open-source ecosystem. Security researchers from multiple firms have identified a threat actor known as TeamPCP, which is behind a wave of supply chain compromises targeting popular npm and PyPI packages. This marks a significant escalation in the methods used to infiltrate software supply chains, leveraging advanced techniques that go far beyond typical credential theft.

mini shai-hulud worm

What makes this campaign particularly alarming is its use of trusted publishing mechanisms and the ability to produce malicious packages that carry valid provenance attestations. The worm spreads itself by locating publishable npm tokens, enumerating packages, and exchanging GitHub OIDC tokens for per-package publish tokens. This self-propagating behavior has earned it the “worm” designation, and it represents a new class of threat that can move laterally across repositories and package ecosystems.

Understanding the Mini Shai-Hulud Worm

The mini shai-hulud worm is not your average malware. Named after the sandworms from Frank Herbert’s Dune universe, it burrows deep into development environments, profiling execution contexts and stealing credentials from cloud providers, cryptocurrency wallets, AI tools, messaging apps, and CI systems. The name is fitting because this worm, much like its fictional namesake, moves beneath the surface, leaving a trail of compromised infrastructure in its wake.

At its core, the worm consists of an obfuscated JavaScript file, often named “router_init.js”, that performs environment reconnaissance. It checks whether it is running inside a Node.js runtime, a browser, or a CI pipeline. Based on the environment, it adapts its behavior. For example, when executed inside GitHub Actions, it targets repository secrets and OIDC tokens. When running on a developer’s machine, it scrapes credentials from installed tools like Claude Code and Visual Studio Code.

The exfiltration channel is equally clever. The malware sends stolen data to the domain “filev2.getsession[.]org”, which uses Session Protocol infrastructure. Session is a decentralized, privacy-focused messaging platform, making its domain unlikely to be blocked by corporate firewalls. As a fallback, the worm commits encrypted data to attacker-controlled GitHub repositories under the author name “claude@users.noreply.github.com”, using stolen GitHub tokens via the GraphQL API.

How the Worm Compromised TanStack

The TanStack compromise is particularly noteworthy because it earned a CVE identifier (CVE-2026-45321) with a CVSS score of 9.6 out of 10.0, indicating critical severity. This incident affected 42 packages and 84 versions across the TanStack ecosystem. The attack chain involved a chained GitHub Actions attack that exploited the “pull_request_target” trigger, cache poisoning, and runtime memory extraction of an OIDC token from the GitHub Actions runner process.

Unlike previous supply chain attacks that used preinstall hooks in package.json, the TanStack variant adopted a different strategy. The attackers included a JavaScript file within the package tarball and added an optional dependency pointing to a GitHub-hosted package. That dependency contained a “prepare” lifecycle hook that executed the JavaScript payload via the Bun runtime. This approach made detection harder because the malicious code was not immediately visible in the package’s main installation script.

TanStack confirmed that no npm tokens were stolen and that the npm publish workflow itself was not compromised. Instead, the attackers staged the malicious payload in a GitHub fork via an orphaned commit. That commit triggered a workflow run against the legitimate TanStack/router workflow because the OIDC trusted publisher was configured at the repository level, not scoped to a protected branch. The workflow run then requested a valid short-lived npm publish token, allowing the attackers to publish compromised versions with valid SLSA Build Level 3 provenance attestations.

The Mistral AI and Other Package Compromises

The updates to the Mistral AI packages followed a more traditional approach. The attackers replaced the contents of the package.json file with a preinstall hook that invoked “node setup.mjs”. This script downloaded the Bun runtime and executed the same JavaScript malware. This technique is more straightforward but still effective, as it runs before the package is fully installed, giving the malware early access to the system.

Beyond TanStack and Mistral AI, the mini shai-hulud worm spread to packages from UiPath, DraftLab, OpenSearch, and Guardrails AI. The worm’s self-propagating nature allowed it to move from one repository to another, finding publishable npm tokens with the “bypass_2fa” flag set to true. It then enumerated the packages owned by those tokens and exchanged GitHub OIDC tokens for per-package publish tokens, effectively hijacking the entire publishing pipeline.

Technical Breakdown: How the Worm Operates

Environment Profiling and Credential Theft

The obfuscated JavaScript file performs a series of checks to understand its execution environment. It looks for environment variables that indicate cloud providers, such as AWS, Azure, or Google Cloud. It checks for cryptocurrency wallet extensions, messaging app tokens, and AI tool configurations. The malware also targets CI systems, particularly GitHub Actions, where it can steal repository secrets and OIDC tokens.

Once credentials are collected, the malware encrypts them and sends them to the attacker’s infrastructure. The use of Session Protocol for exfiltration is a deliberate evasion tactic. Session messages are end-to-end encrypted and routed through a decentralized network, making traffic analysis difficult. Even if a security team detects the outbound connection to “filev2.getsession[.]org”, they may not immediately recognize it as malicious because the domain belongs to a legitimate service.

Persistence Mechanisms in IDEs

The worm establishes persistence hooks in Claude Code and Microsoft Visual Studio Code. These hooks ensure that the malware re-executes every time the developer launches these IDEs. This persistence is achieved by modifying configuration files that run scripts on startup. For VS Code, the malware modifies the workspace settings or extensions to load the malicious code. For Claude Code, it injects commands into the terminal profile.

This approach is particularly insidious because developers often trust their development environments implicitly. They may not notice that a new script is running in the background, especially if it mimics legitimate behavior. The persistence allows the worm to maintain access even after a system reboot, continuously stealing new credentials as they are used.

The Dead-Man’s Switch

Another new behavior introduced in the malware is the installation of a dead-man’s switch. This is a shell script that periodically checks if an npm token created by the malware has been revoked. It does this by polling the npm registry. If the token is still active, the script continues to sleep. If the token is revoked, the script triggers a fallback action, such as alerting the attacker or activating a secondary exfiltration channel.

This mechanism ensures that the attacker knows immediately if their access is cut off, allowing them to take countermeasures before the victim can fully clean the infection. It also helps the worm avoid detection by not making unnecessary network calls when the token is still valid.

The Role of OIDC and Trusted Publishing

The attack is noteworthy for abusing trusted publishing, a feature introduced by package registries like npm and PyPI to improve security. Trusted publishing allows repositories to mint short-lived publish tokens using OIDC (OpenID Connect) without storing long-lived credentials. This is generally considered safer because tokens expire quickly and are scoped to specific packages.

However, the mini shai-hulud worm turned this feature into a liability. By hijacking the OIDC token from a GitHub Actions runner, the attackers were able to request valid publish tokens for any package owned by the compromised repository. They did not need to steal npm tokens because the OIDC permissions allowed them to mint new ones on the fly.

This technique makes the attack extremely difficult to detect because the published packages carry valid SLSA Build Level 3 provenance attestations. SLSA (Supply-chain Levels for Software Artifacts) is a security framework that verifies the integrity of build artifacts. Normally, a valid attestation indicates that the package was built from a specific source commit and has not been tampered with. In this case, the attestations are technically correct because the malicious versions were published through the legitimate build pipeline using hijacked OIDC tokens. This is the first documented npm worm that produces validly attested malicious packages.

Impact on the Open-Source Ecosystem

The consequences of this campaign are far-reaching. The worm has spread beyond the initial targets to packages from UiPath, DraftLab, and other maintainers. Because the worm self-propagates, any repository with a publishable npm token set to bypass 2FA becomes a potential victim. The attack does not require the attacker to have prior access to the repository; the worm itself finds and exploits vulnerable tokens.

For maintainers, this means that a compromised token on one package can lead to the compromise of all packages owned by that token. The worm enumerates packages and publishes malicious versions, potentially affecting thousands of downstream users. The use of valid SLSA attestations makes it harder for automated tools to flag the malicious packages, as they appear to come from a trusted source.

You may also enjoy reading: Age of Empires II: Definitive Ed. Coming to Mac This Month.

End users who install these compromised packages risk having their credentials stolen. The malware targets cloud provider keys, cryptocurrency wallets, AI tool APIs, and messaging app tokens. For organizations that use these packages in their production pipelines, the impact could be severe, leading to data breaches, financial losses, and reputational damage.

Lessons and Recommendations for Developers

Review Your OIDC Configuration

One of the key vulnerabilities exploited by the worm is the repository-level scope of OIDC trusted publishers. TanStack had configured the trusted publisher at the repository level, meaning any workflow running in the repository could request a publish token. The fix is to scope OIDC permissions to protected branches only. GitHub now recommends using environment protection rules to limit which workflows can request OIDC tokens.

To implement this, go to your repository settings and under “Environments”, create a production environment with required reviewers and branch protection. Then, in your publish workflow, reference that environment. This ensures that only workflows triggered from protected branches can mint publish tokens.

Enable Two-Factor Authentication for npm Tokens

The worm specifically looks for npm tokens with “bypass_2fa” set to true. If your organization uses npm tokens, ensure that they require two-factor authentication for publishing. This setting prevents a compromised tokens from being used to publish new versions without a second verification factor. npm has deprecated the bypass_2fa option for new tokens, but existing tokens may still have it enabled.

Audit your npm tokens regularly. Remove any tokens that have “bypass_2fa” set to true, and create new tokens with the “publish” scope and 2FA requirement. Additionally, rotate tokens periodically and revoke any that are no longer needed.

Monitor for Suspicious Workflow Runs

The attack involved an orphaned commit that triggered a workflow run. While GitHub Actions does not prevent orphaned commits from triggering workflows, you can add checks to your workflow YAML to verify the source of the commit. For example, you can use the “github.event_name” context to ensure that the workflow only runs on pull requests or pushes to specific branches.

Consider using the “pull_request_target” trigger with caution. This trigger runs in the context of the base repository, giving it access to secrets. If you must use it, add explicit checks that the pull request is from a trusted user or that the code has been reviewed. The worm exploited the lack of such checks.

Implement Runtime Monitoring in CI

The worm extracts OIDC tokens from the runtime memory of the GitHub Actions runner process. This is a sophisticated technique that is difficult to prevent entirely. However, you can implement runtime monitoring that alerts on unusual process behavior. For example, if a workflow step tries to access the process memory of another step, that should trigger an alert.

Tools like StepSecurity and other CI security platforms can detect such anomalies. They analyze workflow logs and runner behavior to identify malicious activity. Integrating these tools into your pipeline can provide early warning of an ongoing attack.

Use Package Lock Files and Integrity Checks

For downstream consumers, the best defense is to verify package integrity. Use lock files (package-lock.json or yarn.lock) that pin exact versions and hashes. When installing packages, your package manager will check the hash against the lock file. If a malicious version is published with the same version number but different content, the hash mismatch will prevent installation.

Additionally, consider using tools like npm audit or Snyk to scan your dependencies for known vulnerabilities. While the Mini Shai-Hulud worm is new, security vendors are already adding signatures to detect the compromised packages. Regular scanning can catch these threats before they cause harm.

What Makes This Worm Stand Out

Several aspects of the mini shai-hulud worm set it apart from previous supply chain attacks. First, its self-propagating nature means it can spread without direct attacker intervention. Second, its ability to produce validly attested packages undermines the trust that the SLSA framework was designed to provide. Third, the use of decentralized infrastructure like Session Protocol for exfiltration makes it harder to block.

Another new behavior introduced in the obfuscated JavaScript malware is the installation of a dead-man’s switch. This switch ensures that the attacker knows immediately if their token is revoked, allowing them to adapt their strategy. This level of sophistication suggests that TeamPCP is well-resourced and constantly evolving their techniques.

The worm’s ability to persist in IDEs like Claude Code and VS Code means that even after a developer cleans their system, the malware can re-infect if they launch their IDE again. This requires a thorough cleanup that includes removing configuration hooks and verifying extension integrity.

Add Comment