Your IR Runbook Is Now a Weapon: Shai-Hulud's Dead-Man Switch and Editor-Config Persistence
The Escalation
On Wednesday, Shai-Hulud was a credential-theft worm. On Thursday, the new variant ships a destructive-response component. It embeds a gh-token-monitor process that watches for token revocation events, and when a defender rotates a compromised GitHub, npm, or cloud token, the host is wiped. Revocation is the trigger for destruction; that is a design choice in the implant, not a side effect.
Multiple sources independently confirm the behavior and warn that blanket revocation against an infected runner destroys the runner. The revised IR order is isolate → snapshot → enumerate persistence → remove persistence → only then rotate tokens.
Persistence That Survives Uninstall
Removing the malicious npm or PyPI package does not remediate the compromise. The implant writes to three agent-config paths:
.claude/settings.json— re-executes attacker config on every Claude Code launch.vscode/tasks.json— re-executes on every VS Code session.cursor/*— equivalent for Cursor users
These paths sit outside SCA tool scope. npm audit returns clean. Dependabot sees nothing. The host stays compromised through the AI developer tooling engineers run daily, and every IDE launch re-executes attacker-controlled configuration with access to LLM API keys, GitHub PATs, cloud CLI tokens, and production kubeconfigs.
Cross-Source Corroboration
Seven independent sources reported the evolution today. The confirmed blast radius:
| Ecosystem | Affected Packages | Notable Victims |
|---|---|---|
| npm | 400+ (84 malicious TanStack versions, 42 scoped packages) | Mistral AI, UiPath, TanStack |
| RubyGems (GemStuffer) | 150+ gems | UK Council Portal data exfiltrated |
| PyPI | 5+ confirmed | Guardrails AI (0.10.1), OpenSearch |
The TanStack kill chain was CI-native: pull_request_target abuse, GitHub Actions cache poisoning, OIDC token extraction from Runner.Worker memory, exfil via Session/Oxen, and P2P C2 via the GitHub commit-search index. npm 2FA is bypassed entirely.
The attacker has weaponized the defender's revocation response. The incident-response playbook itself is now part of the kill chain.
Detection Engineering for the Persistence Layer
File-integrity monitoring on agent config paths catches what SCA cannot:
- Alert on any write to
.claude/settings.json,.vscode/tasks.json,.cursor/*outside known-good provisioning flows - Hunt for outbound Session/Oxen traffic from CI workers
- Look for unexpected commits to org repos, which is the P2P beacon signal
- Baseline lockfile diffs since May 11 across all repositories
What to do
Rewrite IR runbook for Shai-Hulud-class threats: isolate → snapshot → enumerate persistence → remove persistence → then rotate. Push to all on-call engineers and tabletop today
Deploy FIM rules on .claude/settings.json, .vscode/tasks.json, and .cursor/* across all developer endpoints within 48 hours
Freeze npm and RubyGems dependency updates enterprise-wide; audit all installs between May 11 and today against known-malicious package lists from Aikido, Endor, JFrog, and Socket
Purge GitHub Actions caches and npm caches on all build agents; rotate AWS, GCP, Kubernetes, Vault, GitHub, and SSH credentials on any host that ran npm install against affected versions