axios 是最受歡迎的 JavaScript HTTP 客戶端庫,每週下載量超過一億次。2026 年 3 月 30 日,StepSecurity 發現兩個惡意版本的 axios([email protected][email protected])在 npm 上被發布。這些惡意版本注入了一個新的依賴套件 [email protected],該套件在 axios 原始碼中從未被引用。其唯一目的是執行 postinstall 腳本,作為跨平台遠端存取木馬(RAT)投放器,目標涵蓋 macOS、Windows 和 Linux。該投放器會連接至活躍的指揮控制伺服器,並傳送針對不同平台的第二階段有效載荷。執行後,惡意軟體會自我刪除,並將自己的 package.json 替換為乾淨版本以逃避取證檢測。

如果您安裝了 [email protected][email protected],請假設您的系統已遭入侵。

axios 本身沒有任何惡意程式碼,這正是此攻擊危險之處。兩個被污染的版本皆注入了假依賴 [email protected],該套件從未在 axios 原始碼中被引用,其唯一目的是執行 postinstall 腳本,部署跨平台遠端存取木馬。投放器會連接至指揮控制伺服器,傳送針對 macOS、Windows 和 Linux 的第二階段有效載荷,然後自我刪除並以乾淨的 package.json 取代自身。開發者事後檢查 node_modules 目錄時,無法察覺異常。

這不是偶發事件,而是精準攻擊。惡意依賴在 18 小時前就已準備好,三個平台的有效載荷也事先建置完成。兩個版本分支在 39 分鐘內被同時污染。每個元件都設計成自我銷毀。npm install 後兩秒內,惡意軟體已開始連線攻擊者伺服器,甚至在 npm 完成依賴解析前就已發動。這是針對前十大 npm 套件中最具操作複雜度的供應鏈攻擊之一。

這些入侵由 StepSecurity AI Package Analyst 與 Harden-Runner 偵測到,並已負責任地通報給專案維護者。

Harden-Runner 社群版免費提供給公開倉庫,超過 12,000 個公開專案使用。它在多個開源專案中偵測到 axios 套件異常對攻擊者 C2 網域的外部連線。例如,在廣泛使用的開發者入口框架 backstage 的 CI 過程中,Harden-Runner 偵測到對 sfrclak.com:8000 的 C2 回呼。Backstage 團隊確認該工作流程為沙盒環境,惡意套件安裝不影響專案。該連線因從未出現於先前工作流程而被標記為異常。社群版 Harden-Runner 的偵測結果公開,任何人皆可驗證。

攻擊在約 18 小時內預先部署,惡意依賴先於 axios 版本上架,以避免安全掃描器觸發「全新套件」警報。

攻擊者入侵了 axios 主要維護者 jasonsaayman 的 npm 帳號,並將註冊郵件更改為攻擊者控制的 ProtonMail 地址。利用此權限,同時發布了 1.x 與 0.x 分支的惡意版本,最大化暴露範圍。

兩個惡意版本皆以 jasonsaayman 身份發布,外觀與正規版本無異。發布時未經 GitHub Actions CI/CD 流程,而是使用被盜的 npm 存取權杖手動發布。

npm 註冊資料中可見關鍵取證訊號:所有正規 axios 1.x 版本均透過 GitHub Actions 並使用 npm 的 OIDC Trusted Publisher 機制發布,確保發布與驗證工作流程綁定。[email protected] 則完全跳脫此模式,無 OIDC 綁定且無 gitHead,顯示為手動發布。

axios GitHub 倉庫中無對應 1.14.1 的提交或標籤,該版本僅存在於 npm。合法發布使用的 OIDC 令牌為短暫且限定工作流程範圍,無法被竊取。攻擊者必須取得長期有效的經典 npm 存取權杖。

在發布惡意 axios 版本前,攻擊者先以 [email protected] 帳號發布 [email protected]。該套件的 4.2.0 版本於 18 小時前發布,作為乾淨套件建立發佈歷史,讓 nrwise 看似合法維護者。

[email protected] 與 4.2.1 版本間僅有三處差異,其他 56 個加密原始碼檔案、README、LICENSE 與文件完全相同。加密程式碼與合法 [email protected] 完全一致,攻擊者未修改加密庫程式碼,意在避免差異分析發現異常,焦點反而落在 package.json 的 postinstall 鉤子上。

反取證的 package.md 檔案在 setup.js 執行後會被重新命名為 package.json,版本號仍顯示為 4.2.0,造成二次欺騙。感染後執行 npm list 時會顯示為 4.2.0,導致事件響應者誤判系統未受感染。

攻擊者在 package.json 中新增 plain-crypto-js: "^4.2.1" 作為執行時依賴,該套件從未出現在任何合法 axios 版本中。其他依賴與先前乾淨版本完全相同。

當開發者執行 npm install [email protected] 時,npm 會自動安裝 [email protected],並執行其 postinstall 腳本,啟動投放器。

[email protected] 的 86 個檔案中,plain-crypto-js 從未被 import 或 require,僅存在於 package.json 以觸發 postinstall。此類依賴存在但未使用,是高可信度的入侵指標。

[email protected] 與 1.14.1 版本間唯一變更為 package.json,其他 85 個檔案完全相同。變更包括版本號提升與 plain-crypto-js 依賴新增,並移除 "prepare": "husky" 腳本,顯示發布過程跳過正常開發流程。

[email protected] 至 0.30.4 亦有相同分析,唯一實質變更為惡意依賴注入。

setup.js 為單一壓縮檔案,採用雙層混淆以逃避靜態分析與混淆審查者。所有敏感字串(模組名、作業系統標識、shell 指令、C2 URL、檔案路徑)皆以編碼形式存於陣列 stq[],並由兩個函式於執行時解碼。

投放器入口為 _entry("6202033"),完整 C2 URL 為 http://sfrclak.com:8000/6202033。

StepSecurity 完整解碼 stq[] 陣列,還原整個攻擊流程。

在 macOS 上,投放器會寫入 AppleScript 至 /tmp/6202033,並透過 nohup osascript 靜默執行。該腳本向 C2 發送 POST 請求,下載 macOS RAT 執行檔至 /Library/Caches/com.apple.act.mond(模仿 Apple 系統快取檔案),設定可執行權限並啟動,最後自刪。

com.apple.act.mond 名稱疑似為 "Activity Monitor Daemon" 縮寫,模仿 Apple 反向 DNS 命名慣例。

Windows 平台會在 %PROGRAMDATA% 目錄下建立 wt.exe(PowerShell 複本副本)。

Linux 平台則下載 Python RAT 腳本至 /tmp/ld.py,背景執行並與 npm 進程分離。

各平台向同一 C2 端點發送不同 POST 內容,並使用 packages.npm.org/ 前綴以偽裝為正常 npm 通訊。

投放器執行後會依序進行三個取證清理步驟,將惡意痕跡最小化。

感染後檢查 node_modules/plain-crypto-js/package.json 會發現乾淨清單,npm audit 亦無異常。唯一持續證據為 node_modules/plain-crypto-js 目錄存在,因該套件非任何合法 axios 版本依賴。

StepSecurity 透過 GitHub Actions 中的 Harden-Runner 實際執行 [email protected],捕捉所有外部網路連線、進程與檔案寫入,完整還原 npm install 過程中惡意軟體行為。

Harden-Runner 公開該次執行的詳細資訊,顯示兩次對 sfrclak.com:8000 的外部連線,且連線發生時機顯示惡意軟體已脫離原始流程樹,成功逃避追蹤。

進程樹與檔案事件日誌確認惡意軟體執行鏈與反取證技術,包含投放器執行時間與 package.json 替換。

若要判斷組織是否受影響,請檢查代碼庫、CI/CD 流程與開發者機器。惡意版本上架時間不到 3 小時,但任一 npm install 即可能觸發木馬。

可利用 GitHub 代碼搜尋查找 package.json 或 package-lock.json 中是否引用受影響版本,並確認結果是否為真實依賴。

本地可檢查 node_modules 是否存在 plain-crypto-js 目錄,該目錄存在即代表投放器已執行。

檢查 CI/CD 日誌中是否有在惡意版本上架期間執行 npm install,任何安裝惡意版本的流水線均視為受感染。

持續運行的自建 CI runner 視同開發者機器,需依照開發者機器修復步驟處理。臨時 runner(如 GitHub-hosted)則在任務結束後銷毀,但應立即更換所有注入的秘密與憑證。

開發者機器是供應鏈攻擊中常被忽略的攻擊面。任何在本地執行過受感染 axios 版本的開發者機器均可能被入侵。

修復步驟包括:

1. 立即隔離機器,斷開網路連線。

2. 清點所有秘密與憑證。

3. 重格式化並從已知安全狀態重建。

4. 從乾淨機器更換所有憑證,並檢查異常存取日誌。

建議在所有環境封鎖對攻擊者 C2 基礎設施的外部流量。

大多數惡意 npm 套件會在發布後數小時內被移除。配置冷卻期與最小版本年齡政策可防止自動採用新發布的套件,降低風險。

主要 Node.js 套件管理器(npm、pnpm、Yarn、Bun)均支持版本發布年齡限制,作為多層防禦策略的一環。

StepSecurity 在威脅中心發布了相關威脅情報,提供完整攻擊摘要、技術分析、IOC、受影響版本與修復步驟,方便團隊即時應對。

Harden-Runner 是專為 CI/CD runner 設計的安全代理,強制執行網路出口允許清單,阻止未授權的外部連線,防止資料外洩。

Harden-Runner 也會自動記錄每個工作與倉庫的外部網路流量,建立正常行為模式並標記異常,即使惡意軟體自我刪除證據也能偵測。

供應鏈攻擊不僅止於 CI/CD 流程。[email protected] 的 postinstall 腳本會在開發者本機植入跨平台遠端存取木馬,竊取憑證、SSH 金鑰、雲端令牌等敏感資訊。

StepSecurity Dev Machine Guard 可即時監控所有註冊開發者設備上的 npm 套件,發現惡意套件時可快速定位受影響機器。

新發布的 npm 套件會在冷卻期內暫時被阻擋,避免惡意套件被自動採用。此次事件中,[email protected] 在 axios 受感染版本前數小時發布,冷卻機制可有效防範。

StepSecurity 持續更新惡意與高風險 npm 套件資料庫,PR 嘗試引入受感染套件時會自動阻擋合併。

AI Package Analyst 即時監控 npm 註冊表,發布後數分鐘內即標記 [email protected][email protected] 為高風險,讓團隊有時間調查與應對。

感謝 axios 維護者及社群成員迅速識別並處理此入侵事件,協助生態系統快速理解威脅並採取行動。

也感謝 GitHub 迅速停用受感染帳號,npm 迅速下架惡意版本並對 plain-crypto-js 實施安全封鎖,協調反應大幅縮短全球開發者暴露時間。