Portfolio
Threat Analysis  ·  Supply Chain  ·  Nation-State

60 Seconds
How North Korea Hijacked a Library Used by 100 Million Developers — and Why It Took Three Hours to Notice

Analyst
Yana Ivanov
Published
April 2026
Classification
Public — Educational
Threat Actor
UNC1069 / BlueNoroff
Target
axios npm package
Malware
WAVESHAPER.V2 RAT
Active IOCs — sfrclak[.]com · 142.11.206.73 · axios@1.14.1 · axios@0.30.4 — All affected versions removed from npm registry
Section 01

A Library the World Trusted, a Backdoor
Nobody Saw Coming

At 00:21 UTC on March 31, 2026, a North Korea-nexus threat actor silently pushed two backdoored versions of axios — the most widely used JavaScript HTTP client in the world — to the npm registry. The malicious versions contained a hidden dependency that no one in the axios codebase had authored, reviewed, or approved. For the next three hours, every developer, build pipeline, and CI/CD system that ran npm install silently received a cross-platform remote access trojan.

The attack was not a zero-day exploit. The axios library itself was not vulnerable. No one's firewall failed. The trust chain failed. An attacker compromised a single npm maintainer account and weaponized the implicit trust that over 100 million weekly downloads had earned over years of legitimate use. The code was fine. The delivery mechanism was not.

Google Threat Intelligence Group attributed the attack to UNC1069, a financially motivated North Korea-nexus actor linked to BlueNoroff — a well-documented Lazarus Group subunit specializing in cryptocurrency theft and financial sector intrusion. The malware deployed was WAVESHAPER.V2, an evolution of a RAT previously used in prior BlueNoroff campaigns. It beaconed home every 60 seconds.

This report examines who did this and why, how the attack was constructed step by step, what the malware does and what it looks like in traffic, why detection took three hours rather than three minutes, and what organizations — particularly defense contractors whose developers depend on JavaScript tooling — can do to detect and prevent the next iteration.

Attack at a Glance
3hrs
Window of exposure
00:21 to 03:20 UTC, March 31, 2026
100M+
Weekly downloads at risk
axios is the most downloaded JS HTTP client
18hrs
Pre-staging window
Phantom dependency published before the attack
60sec
C2 beacon interval
WAVESHAPER.V2 phoned home every 60 seconds
Section 02

Who Is UNC1069 — and Why Are They
Targeting Developer Tools?

UNC1069 is a financially motivated threat actor that Google Threat Intelligence Group has tracked since at least 2018. The group operates within the North Korean intelligence apparatus — specifically linked to BlueNoroff, a specialized subunit of the Lazarus Group that operates under the Reconnaissance General Bureau, North Korea's primary foreign intelligence service.

BlueNoroff's mandate is financial. Unlike other Lazarus subunits focused on espionage or destructive attacks, BlueNoroff generates hard currency for the North Korean state — primarily through cryptocurrency theft, financial sector intrusion, and increasingly, supply chain compromise. The funds finance North Korea's weapons programs. This is not criminal activity incidental to the state. It is state activity conducted through criminal methods.

UNC1069's historical TTPs show a group that adapts its delivery mechanisms while maintaining consistent objectives. Prior campaigns used AI-generated deepfake videos and fabricated meeting invitations to target executives at cryptocurrency and decentralized finance firms. The axios attack represents an evolution: rather than targeting individual high-value victims through social engineering, UNC1069 chose to compromise a single widely trusted delivery mechanism and let the global developer community distribute the payload on their behalf.

Strategic Shift: UNC1069 has moved from targeting individuals through deception to targeting infrastructure through trust. The attack surface has changed from human judgment to automated systems — build pipelines, dependency managers, and CI/CD workflows that install packages without human review.

The Coordination Question — UNC1069 and TeamPCP

Google's assessment formally separates UNC1069 from TeamPCP (UNC6780), the North Korea-nexus group behind the recent Trivy vulnerability scanner compromise and subsequent attacks on PyPI packages associated with projects including LiteLLM and Checkmarx. GTIG explicitly stated the axios attack is "unrelated to the recent TeamPCP supply chain issues."

The technical separation is accurate — the malware, infrastructure, and TTPs are distinct. But treating these as entirely independent operations may underestimate the coordination capability of North Korean offensive cyber programs. Both groups operate within the same intelligence apparatus, under the same command structure, with the same financial mandate. The Reconnaissance General Bureau does not run its cyber units as truly independent commercial entities.

TeamPCP's recent operations harvested over 500,000 corporate identities including developer credentials, API tokens, and publishing keys from compromised developer environments. If any portion of that credential harvest included npm publishing tokens — plausible given that developer tools were the specific targets — those credentials could have been shared or sold within the North Korean intelligence apparatus, potentially informing or enabling the axios maintainer account compromise.

Analytical Note: The temporal proximity of two separate North Korean supply chain attacks against the same npm ecosystem within days of each other warrants consideration of whether intelligence sharing occurred between UNC1069 and UNC6780. Nation-state cyber units within the same command structure routinely share operational intelligence. The alternative — that two North Korean groups independently chose to attack npm within the same week purely by coincidence — is the less parsimonious explanation.

Section 03

The Attack, Step by Step — How a Trusted Package Became a Weapon

The axios attack succeeded not because of a technical vulnerability but because of a systemic assumption: that packages from trusted maintainers with long publishing histories are safe to install. Understanding how the attack was constructed reveals why that assumption is insufficient and what controls would have broken the kill chain.

Step 01
ACCOUNT COMPROMISE

npm maintainer credentials stolen via unknown credential theft vector. Attacker changed the account email to an attacker-controlled ProtonMail address and obtained a long-lived access token — bypassing the OIDC publishing protections entirely because the legacy token took precedence.

Step 02
PRE-STAGING

plain-crypto-js@4.2.1 published to npm 18 hours before the attack — not to build fake usage history, but to give the package any npm presence at all. Enough to pass zero-history detection checks that would flag a brand-new account injecting itself into a 100M-download library.

Step 03
PAYLOAD INJECTION

Malicious axios versions 1.14.1 and 0.30.4 published at 00:21 UTC with plain-crypto-js injected as a dependency. Both release branches hit within 39 minutes. Any developer or CI/CD pipeline running npm install against either version silently received the dropper.

Step 04
SILENT EXECUTION

npm's postinstall hook automatically executed setup.js the moment the package was installed — no user interaction, no prompt, no warning. The dropper checked the target OS, fetched the platform-specific payload, deployed WAVESHAPER.V2, then deleted itself and overwrote package.json with a clean version.

Step 05
RAT DEPLOYED

WAVESHAPER.V2 active on Windows, macOS, and Linux. Persistence established via registry run key named MicrosoftUpdate. Dropper evidence erased. RAT begins beaconing to sfrclak[.]com on port 8000 — every 60 seconds, waiting for instructions.

The Pre-Staging Deception — What "Building History" Actually Means

Eighteen hours before the attack, UNC1069 published plain-crypto-js@4.2.1 to the npm registry as a standalone package. This was not fake usage history — the package had no meaningful download statistics. The purpose was narrower: to ensure the package was not flagged as a zero-history account publishing to a major dependency for the first time.

Some automated security scanners flag dependencies that come from packages with no prior npm presence whatsoever — a brand-new account injecting itself into a library with 100 million weekly downloads is an obvious signal. By publishing 18 hours early, UNC1069 gave the malicious package an npm existence, a version number, and a publication timestamp. Enough to pass the most basic zero-history checks.

The name itself deserves analysis. In developer contexts, crypto refers to cryptography — the mathematical science of securing data — not cryptocurrency. The Node.js built-in cryptography module has been called crypto for decades. A package with crypto in its name would not raise immediate red flags among developers working with security primitives. But plain-crypto-js contains a semantic contradiction: plain means unencrypted, crypto means encrypted. A legitimate developer would not name a cryptographic utility plain-crypto. The attackers understood their audience precisely well enough to choose a name that would appear plausible to developers while being technically incoherent to anyone who stopped to read it carefully.

✓ Legitimate Dependency

Name makes sense for the parent package's purpose.

axios is an HTTP client. Legitimate dependencies handle things like HTTP adapters, form data, URL encoding.

Established history proportional to the parent package's age and download volume.

No postinstall scripts making outbound network connections.

✗ plain-crypto-js (Malicious)

Semantically incoherent name — "plain" contradicts "crypto".

An HTTP client has no legitimate need for a cryptographic dependency. Purpose mismatch is an immediate red flag.

Zero history before 18 hours prior to the attack. Published specifically to pass basic checks.

postinstall hook executes setup.js which makes outbound C2 connections.

The Long-Lived Token Problem

The axios maintainer had multi-factor authentication configured. OIDC-based short-lived tokens were set up for the publishing workflow. On paper, the account security was reasonable. The attack succeeded anyway because a long-lived npm access token — the kind that never expires unless manually revoked — was still present alongside the OIDC configuration. When both exist, npm uses the long-lived token. The OIDC protections were effectively bypassed by a credential that should not have existed.

The attacker changed the maintainer's email address to an attacker-controlled ProtonMail account and used the stolen long-lived token to publish directly via the npm CLI, entirely bypassing the GitHub Actions publishing workflow where the OIDC controls lived. The security was on the right path. The residual long-lived token was the gap.

The Core Failure: Long-lived credentials are a liability that accumulates risk over time. A token that never expires is a permanent key. Every day it exists is another day it can be stolen and used. The axios attack was made possible by a credential that should have been rotated out of existence.

Section 04

WAVESHAPER.V2 — What the RAT Does and What It Looks Like

WAVESHAPER.V2 is not a keylogger. Calling it a keylogger significantly undersells its capabilities and leads to underestimating the severity of an infection. It is a fully functional remote access trojan — a persistent, cross-platform backdoor that gives the attacker complete control over any system it runs on.

The dropper (SILKBELL / setup.js) checks the target operating system upon execution and delivers platform-specific payloads. On Windows, it copies the legitimate PowerShell executable to %PROGRAMDATA%\wt.exe disguised as Windows Terminal and uses a VBScript launcher. On macOS it masquerades as a system daemon. On Linux it drops a Python RAT to /tmp/ld.py launched via nohup. After delivering its payload, the dropper deletes itself and overwrites package.json with a clean version containing no postinstall reference — eliminating forensic traces of how the infection occurred.

Persistence — This Does Not Go Away on Reboot

Unlike Meterpreter, which lives purely in memory and disappears on reboot, WAVESHAPER.V2 establishes persistence mechanisms specifically designed to survive system restarts. On Windows, it creates a hidden batch file at %PROGRAMDATA%\system.bat and adds a registry run key named MicrosoftUpdate under HKCU\Software\Microsoft\Windows\CurrentVersion\Run. Every time the system boots, WAVESHAPER.V2 restarts automatically. The name MicrosoftUpdate is deliberate — it blends with the kind of registry entry that legitimate software creates, reducing the chance a cursory review flags it.

The Beacon — 60 Seconds, Every Time

Once deployed, WAVESHAPER.V2 beacons to its command and control server every 60 seconds using Base64-encoded JSON sent over port 8000. Each beacon includes system telemetry: hostname, username, boot time, timezone, OS version, and a detailed list of running processes. The C2 server responds with instructions — run a command, inject code into a process, enumerate the filesystem, or do nothing and wait for the next check-in.

The User-Agent string is among the most immediately detectable elements: the RAT identifies itself as Internet Explorer 8 running on Windows XP. No legitimate software in 2026 sends that User-Agent. Any SOC analyst, any IPS rule, any SIEM query looking at User-Agent strings should flag this immediately.

WAVESHAPER.V2 — Traffic Signature
Signal Value Why It Matters Severity
Destination Port 8000 Unusual for production traffic. Not a standard web service port. High
Beacon Interval 60 seconds exactly Machine-precise regularity. No human-generated traffic is this consistent. Critical
User-Agent MSIE 8.0 / Windows XP IE8 on XP in 2026. No legitimate software sends this. Immediate escalation required. Critical
Destination Raw IP — no domain Legitimate traffic resolves hostnames. Direct IP connections evade DNS-based filtering. Critical
Body Encoding Base64 JSON Encoded payloads obscure content from inspection. Common C2 obfuscation technique. High
Initiating Process powershell.exe / wt.exe PowerShell making outbound connections on port 8000 is anomalous in most environments. Critical

Wireshark Detection Filter

The following Wireshark display filter will surface WAVESHAPER.V2 C2 traffic using the documented behavioral indicators. Analysts capturing traffic on networks where affected axios versions may have been installed should apply this filter:

// WAVESHAPER.V2 C2 Detection — Wireshark Display Filter // Matches beacon traffic by port, destination pattern, and known C2 IP tcp.dstport == 8000 or ip.dst == 142.11.206.73 or (http.user_agent contains "MSIE 8.0") or (http.request.method == "POST" and not http.host) // Combined high-confidence filter: tcp.dstport == 8000 and (http.request.method == "POST" or not dns)

KQL Detection Rule — Microsoft Sentinel

For organizations running Microsoft Sentinel, the following KQL queries detect WAVESHAPER.V2 persistence and C2 beaconing:

// Detect MicrosoftUpdate persistence registry key DeviceRegistryEvents | where RegistryKey contains "CurrentVersion\\Run" | where RegistryValueName == "MicrosoftUpdate" | where InitiatingProcessFileName in ("powershell.exe", "wt.exe", "wscript.exe") | project Timestamp, DeviceName, RegistryKey, RegistryValueName, InitiatingProcessFileName // Detect outbound C2 beaconing on port 8000 DeviceNetworkEvents | where RemotePort == 8000 | where InitiatingProcessFileName in ("powershell.exe", "wt.exe", "python.exe") | where RemoteIPType == "Public" | summarize ConnectionCount = count() by DeviceName, RemoteIP, bin(Timestamp, 1m) | where ConnectionCount >= 1 | project Timestamp, DeviceName, RemoteIP, RemotePort, ConnectionCount
Section 05

Why Did It Take Three Hours —
The Four Detection Gaps

Three hours is fast by historical standards for supply chain compromises, which have gone undetected for months or years. StepSecurity, a firm that monitors npm publishing patterns, caught the unexpected dependency within the exposure window. But for organizations whose build pipelines pulled the affected versions before detection, three hours was long enough. Understanding why detection was not faster reveals the specific gaps that made this attack hard to catch in real time.

  • Critical
    No WAVESHAPER.V2 Signatures Existed at Attack Start

    At 00:21 UTC when the attack began, WAVESHAPER.V2 was an updated variant. IPS signature databases, EDR platforms, and antivirus engines did not contain detection rules for it. Signature-based detection fundamentally cannot catch a threat it has never seen. The gap between a new variant appearing and signatures being written and distributed is always an exposure window. In this case that window was the entire three-hour attack duration.

  • Critical
    CI/CD Pipelines Have Different Security Visibility Than Workstations

    Many victims were not individual developers but automated build systems running npm install as part of continuous integration workflows. These pipelines are designed to execute system commands — that is their function. An IPS watching a build pipeline sees expected behavior: a process running, network connections being made, files being written. Without specific behavioral rules tuned to flag C2 beaconing from build environments, the malicious activity blended into normal pipeline execution.

  • High
    The Dropper Eliminated Its Own Forensic Evidence

    By the time any analyst began investigating, setup.js was gone. The postinstall script had been removed. package.json had been overwritten with a clean version. The chain of events that explained how the infection happened had been deliberately erased. What remained was a running RAT with no obvious explanation of its origin — significantly complicating both triage and attribution at the individual system level.

  • High
    The Traffic Signals Were Individually Ambiguous

    Port 8000 outbound traffic is unusual but not blocked by default. PowerShell making network connections is common. Base64-encoded POST bodies are used by legitimate applications. No single signal was definitively malicious in isolation. Detection required correlating multiple signals simultaneously — port, process, encoding, destination, regularity — into a composite alert. Organizations without behavioral correlation rules tuned to catch this specific combination missed it in the noise.

What Would Have Caught It in Minutes: A Sentinel analytic rule monitoring for registry key creation under HKCU\...\Run with the value name MicrosoftUpdate initiated by PowerShell would have fired the moment WAVESHAPER.V2 established persistence — likely within the first five minutes of infection. The persistence mechanism is the earliest durable artifact the RAT creates. Detection rules targeting persistence behaviors, not malware signatures, are more resilient to variant evasion.

Section 06

From WAVESHAPER to WAVESHAPER.V2 — Why Signatures Fail and What Comes Next

WAVESHAPER.V2 is an evolution of WAVESHAPER, a RAT previously used in prior BlueNoroff campaigns. The core functionality is consistent across versions — beaconing, command execution, process injection, reconnaissance, persistence. What changed is the code implementation: enough modification to generate a different hash, defeat signature-based detection, and require new YARA rules to be written before automated systems could catch it.

This is the fundamental limitation of signature-based detection: it is a museum of known threats. Every new variant that modifies its implementation, however slightly, starts the museum-building process again. The attacker modifies, the defender writes new signatures, the attacker modifies again. The attacker moves first. The defender always reacts.

Behavioral detection inverts this dynamic. Rather than matching what malware looks like, behavioral detection matches what malware does. WAVESHAPER and WAVESHAPER.V2 both beacon to a C2 server at precise intervals. Both inject into legitimate processes. Both create registry persistence keys with legitimate-sounding names. Both use encoded POST bodies. Those behaviors are consistent across variants — and they are detectable without knowing what the malware is called.

This is where machine learning is actively transforming the field. Platforms like CrowdStrike Falcon and Darktrace build behavioral baselines from billions of observed data points and flag deviations — not because they recognize WAVESHAPER.V2 specifically, but because a process making machine-precise 60-second outbound connections using a 16-year-old browser identity to a raw IP address on an unusual port is anomalous regardless of what the underlying malware is named. The question is not "is this WAVESHAPER?" but "is this normal?" The answer in every compromised environment was unambiguously no.

The AI Frontier: Researchers are applying transformer-based sequence models — the same architecture underlying large language models — to malware analysis. Code execution traces, API call sequences, and network traffic patterns have sequential structure that these models can learn from. A model trained on WAVESHAPER's behavioral DNA would recognize WAVESHAPER.V2 not by signature but by the pattern of what it does. This approach is active research with commercial products emerging. The arms race between offense and defense is increasingly being fought with the same AI tools.

Section 07

What Should Have Happened —
and What to Do Now

The axios attack was not inevitable. At multiple points in the kill chain, specific controls would have broken the attack or significantly accelerated detection. The following recommendations are ordered by impact and urgency, with particular attention to defense contractors whose development teams depend on open-source JavaScript tooling.

01
Eliminate Long-Lived Publishing Tokens Immediately CM.2.061

Audit all npm, PyPI, and GitHub publishing accounts for long-lived access tokens. Revoke them. Replace with OIDC-based short-lived tokens that expire after a single use or a defined window. A token that cannot survive a rotation cannot be stolen and used indefinitely. This is the single highest-impact change a development organization can make today.

02
Deploy Behavioral Detection Rules for Persistence Mechanisms SI.2.216

Write and deploy Sentinel or Splunk analytic rules that flag registry run key creation by unusual initiating processes. The MicrosoftUpdate key created by PowerShell is not something legitimate Windows Update does. Behavior-based persistence detection would have fired within minutes of infection, before WAVESHAPER.V2 completed its first beacon cycle.

03
Implement Dependency Verification in CI/CD Pipelines SA.4.171

Integrate tools like Socket.dev, Snyk, or Dependabot into build pipelines with blocking — not just alerting — configuration. Flag any new dependency added to an established package that has no logical relationship to that package's purpose. Flag packages with publishing history shorter than the parent package's age. Require human review for unexpected dependency additions before build proceeds.

04
Monitor Outbound Traffic for Beaconing Patterns

Deploy network monitoring rules that flag machine-precise outbound connection intervals. A process connecting to an external IP on port 8000 every 60 seconds exactly is not human-generated traffic. Darktrace and similar platforms detect this pattern automatically. For organizations without ML-based network monitoring, a basic SIEM rule correlating connection regularity with unusual ports catches this class of behavior.

05
Rotate All Credentials Used in Affected Environments

Any system that ran npm install against axios@1.14.1 or axios@0.30.4 during the exposure window should be treated as fully compromised. Rotate every secret, API key, deploy key, and credential that process had access to. Rebuild from clean snapshots where possible. The RAT's reconnaissance capabilities mean it enumerated all accessible credentials during its dwell time.

06
Subscribe to Threat Intelligence Feeds for npm Monitoring

Platforms including AlienVault OTX and the GitHub Advisory Database publish IOCs within hours of confirmed supply chain compromises. Automated ingestion of these feeds into SIEM detection rules means confirmed attack infrastructure — like the C2 IP 142.11.206.73 and domain sfrclak[.]com — triggers alerts automatically the moment they appear in threat intelligence rather than requiring manual rule updates.

Confirmed IOCs — Block and Monitor

Indicator Type Action Source
sfrclak[.]com C2 Domain Block at DNS and firewall. Monitor for historical connections. Confirmed
142.11.206.73 C2 IP Address Block outbound on all ports. Alert on any historical connection logs. Confirmed
axios@1.14.1 npm Package Identify all systems that installed this version. Treat as compromised. Confirmed
axios@0.30.4 npm Package Identify all systems that installed this version. Treat as compromised. Confirmed
plain-crypto-js@4.2.1 npm Package Remove from node_modules. Presence confirms dropper execution. Confirmed
HKCU\...\Run\MicrosoftUpdate Registry Key Presence confirms WAVESHAPER.V2 persistence. Immediate incident response. Critical
%PROGRAMDATA%\system.bat File Artifact Hidden batch file. Presence confirms active infection. Critical
Section 08

The Trust Problem Is the Real Vulnerability

The axios attack did not exploit a bug. It exploited an assumption — that packages from trusted maintainers with long histories are safe to install without inspection. That assumption is structural to how modern software development works. Developers install hundreds of dependencies without reading their code. Build pipelines run npm install without human review of every transitive dependency. The efficiency gains are real. So is the attack surface.

North Korean offensive cyber operations have identified this structural trust as a primary attack vector. UNC1069's choice to compromise a single npm maintainer account rather than targeting individual victims reflects a sophisticated understanding of leverage: one compromised account, one popular package, and the global developer community becomes your delivery mechanism. The attacker does not need to reach each victim. The victims install the payload themselves, automatically, because they trust the ecosystem.

The 60-second beacon is the clearest metaphor for what this attack represents. Once deployed, WAVESHAPER.V2 checked in with its operators every minute, waiting for instructions. Every 60 seconds, on every compromised system, it announced: I am here. What do you want me to do? For every system where detection and response did not happen within those 60-second windows, the attacker had another opportunity. The question for every organization that uses npm — which is most of them — is whether their detection capability can close that window before the instructions arrive.

For Defense Contractors Specifically: JavaScript tooling is deeply embedded in modern software development, including in environments that build systems for classified programs. A compromised developer workstation is not just an IT problem — it is a potential supply chain compromise of the software being developed. The same patterns used to compromise axios could be used to compromise internal tooling, internal package registries, or build pipelines that touch controlled unclassified information. The threat is not theoretical. It is active, capable, and patient.

Hands-on detection lab: Lab Log 009 — WAVESHAPER.V2 Traffic Analysis demonstrates how to detect this attack in Wireshark using behavioral filters, applies the detection filters documented in this report to a synthetic training pcap, and shows why pre-built behavioral rules catch this threat faster than IOC-specific signatures.

YI
Yana Ivanov
Security Analyst  ·  CMMC Compliance Consultant  ·  SiteWave Studio

Yana Ivanov is a security analyst and CMMC consultant based in Connecticut, specializing in cybersecurity risk assessment for defense contractors in the Connecticut defense industrial base. With 15 years of enterprise technology experience and an MS in Information Systems, she brings a practitioner perspective to threat intelligence analysis. She is currently pursuing CompTIA Security+ and CMMC Registered Practitioner certification, with a focus on helping defense supply chain companies achieve genuine — not checkbox — security compliance. This analysis was produced independently as a contribution to the security community's understanding of active threats against US defense infrastructure.

Portfolio