打开网易新闻 查看精彩图片

4亿次月下载,100万周活跃用户,这个数字放在任何产品里都是天文级体量。但当它被黑客盯上,攻击面也被同步放大。

今天凌晨,JavaScript生态最主流的HTTP客户端库Axios遭遇供应链投毒。攻击者在3小时内向npm仓库推送了两个恶意版本,目标覆盖Linux、Windows、macOS全平台——这不是普通的漏洞,而是一场针对开发者工作流的精准伏击。

攻击时间线:从账号接管到全平台投毒

根据Endor Labs、Socket、Aikido和StepSecurity四家安全公司的联合追踪,攻击发生在UTC时间00:21至01:00之间。第一个恶意版本axios@1.14.1于00:21发布,不到一小时后,axios@0.30.4紧随其后。

两个版本都缺少OIDC(OpenID Connect,开放式身份认证)包来源验证,也没有对应的GitHub提交记录——这本该是触发安全警报的明显信号。但npm的自动化防护并未拦截。

攻击者得手的关键,在于控制了Axios核心维护者Jason Saayman的npm账号。OpenSourceMalware社区进一步发现,Saayman的GitHub账号同样沦陷:邮箱被篡改为ifstap@proton.me,一位项目协作者DigitalBrainJS试图在GitHub上回复漏洞报告,却发现报告已被攻击者删除。

账号接管→仓库控制→版本投毒,这条攻击链在开源生态里并不新鲜。但Axios的体量让这次事件的潜在影响被指数级放大。

打开网易新闻 查看精彩图片

投毒手法:不碰核心代码,藏在依赖里

投毒手法:不碰核心代码,藏在依赖里

攻击者的技术选择很有意思。他们没有直接修改Axios的业务代码,而是在package.json里注入了一个名为plain-crypto-js@^4.2.1的恶意依赖。

这个依赖在安装阶段执行post-install脚本,启动一个经过混淆的投放器(setup.js)。投放器会联系远程命令控制服务器(C2),根据检测到的操作系统下载对应的第二阶段载荷。

Windows端的操作最为繁复:混合使用VBScript和PowerShell,先弹出一个隐藏的命令行窗口,然后把PowerShell复制到%PROGRAMDATA%\wt.exe实现持久化——这个路径命名明显是在模仿Windows Terminal(wt.exe),属于典型的伪装手法。最后下载并执行远程脚本。

macOS端相对简洁:用AppleScript把二进制文件写到/Library/Caches/com.apple.act.mond,标记为可执行后后台运行。路径里的com.apple.act.mond看起来像是系统组件,实则是凭空构造的标识符。

Linux端则直接拉取一个Python脚本到/tmp/ld.py,用nohup命令后台执行。ld.py这个命名可能是在模仿动态链接器(ld.so),对不熟悉系统底层的开发者有一定迷惑性。

三端的最终目标一致:植入远程访问木马(RAT,Remote Access Trojan),让攻击者能够持续执行命令、维持对受感染主机的控制。RAT还支持拉取base64编码的二进制文件并执行,意味着攻击者可以随时更新功能模块。

打开网易新闻 查看精彩图片

为什么开发者很难防住

为什么开发者很难防住

这次攻击的阴险之处在于,它利用了JavaScript生态的"信任惯性"。

Axios作为基础设施级依赖,被无数项目间接引入。开发者很少会锁定patch版本,package.json里写的^1.14.0会在安装时自动匹配1.14.1——这个设计本意是自动获取安全修复,这次却成了自动获取恶意代码的通道。

post-install脚本更是npm生态的长期争议点。安装依赖时自动执行代码,这本是为了方便原生模块编译,却被攻击者当成了完美的投递入口。普通开发者查看node_modules的概率,大概和查看外卖骑手健康证的概率差不多。

攻击者选择plain-crypto-js这个名字也很讲究。crypto-js是正经的加密库,plain-crypto-js看起来像是它的变体或轻量版,容易让人误以为是什么必要的子依赖。

目前尚不清楚有多少下游项目在3小时的暴露窗口期内中招。但考虑到Axios的400万月下载量,实际影响可能相当可观——尤其是那些依赖自动构建流程、缺乏版本锁定的CI/CD管道。

Jason Saayman的账号是如何被攻破的,目前没有公开细节。是钓鱼邮件、密码重用、还是npm平台的认证漏洞?这个问号背后,藏着整个开源供应链的脆弱性。

当你的构建脚本开始下载东西时,它到底是在为你工作,还是在为某个ProtonMail邮箱背后的陌生人工作?