你装的扩展,不一定是作者发的那份

Hello,我是飞飞。
10 月 29 日,Cursor 的扩展市场里出了一个假版本。那个插件叫 Anthropic.claude-code,假版本挂了 11 个小时。
你如果在那天更新过这个扩展,装上的可能不是 Anthropic 发的那份。
我用 Claude Code,也在 Cursor 里装过它。看到公告,我没先想“谁这么大胆”。我想的是另一句。我凭什么认定,编辑器里那份就是 Anthropic 发的?
结论先放这儿:模型没被投毒。被改写的是送到你机器上的那条分发链路。扩展更新,就是一次代码执行。
11 小时里发生了什么
Cursor 的公告写得很具体。10 月 29 日,太平洋时间凌晨 2 点 27 分到下午 1 点 35 分。两个版本 2.1.312 和 2.1.313 出现在它的扩展市场。覆盖 macOS 的 ARM 包和 Windows 的 x64 包。Cursor 明确说,这两个版本不是 Anthropic 开发的。
那 11 个小时里,装的人看到的发布者是 Anthropic。下载到的,却是被别人改过的包。
11 个小时不算长。可扩展更新通常是静默的。不弹窗,也不问你同不同意。这期间编辑器只要重启过一次。更新就可能装上了。
恶意代码干的事,公告列了三件:
- 收集主机和用户信息:主机名、用户名、系统、架构、家目录、环境变量名、工作目录、Git 邮箱、公网 IP。
- 往 SSH 授权文件里塞一把攻击者的公钥,注释叫 svc-telemetry。再试着打开本机 SSH 服务,拉一条反向隧道。说人话,就是从你机器连回攻击者服务器的一条通道。
- 写持久化。macOS 上放一个叫 com.apple.sysmond 的开机自启项。Windows 上建一个叫 SysMon 的计划任务,每 60 秒重试。
有个细节容易被略过。Cursor 说恶意代码自己有 bug。打开 SSH 服务也需要管理员权限。按 Cursor 的说法,多数机器上那一步会失败。反向隧道大概率没建起来。
公告紧接着提醒了一句。公钥可能已经写进去了。持久化文件也可能已经落下。主机信息同样可能已经发出去了。只卸载扩展不够。恶意代码会留下独立运行的脚本。
所以“没得手”和“没发生”是两件事。前者靠运气,后者才是你能核的。
Cursor 的博客没写受影响人数。它在 X 上出现过两个数:4100 和 5000。两个都带“最多”的意思。两条 X 帖我没能核到原文,只能把这两个数都当上界。
代收点递错了包裹
小区门口的快递代收点,面单上写着寄件人。你扫一眼,觉得没问题,就拿回家了。你信的是面单。拿到手的,是代收点递过来的盒子。
编辑器扩展市场就是这个代收点。扩展 ID 写着 Anthropic.claude-code,图标、名字、介绍都对。你点更新的时候,看到的是名字,哈希没人对。
你信任的是发布者。实际运行的,是渠道递过来的那份代码。
更麻烦的是,扩展不是普通文件。它跑在编辑器的扩展进程里。能读工作目录、环境变量、Git 配置,也能执行命令。
装一个扩展,等于同意一段陌生代码。这段代码还会持续更新,在你的开发环境里运行。它拿不到管理员权限。但也能看到你开了哪些环境变量。
Cursor 下架了恶意版本,整体关停了市场。轮换密钥、重建之后,它又把市场放回来。它还让托管商把攻击服务器下线。公告里说,访问记录也审计过。没有发现其他扩展被改。
它没说恶意包是怎么进市场的。是账号被拿?是构建环节被动手?还是内部流程出了洞?公告里没有答案。
这个空白值得记住。它决定了你的判断。是偶发事故,还是流程失守。
九起事故,同一种猎物
安全公司 Wiz 在 10 月 30 日发了一份报告。他们数了整个十月。至少九个 AI 开发者平台披露了安全事件。名单里有 Fireworks AI、Andromeda、Zeabur、Lightning AI、OpenCode、Railway、Warp、CommandCode、Northflank。
这些事件的根因并不一样:
- 有的指向凭据访问。
- 有的指向构建基础设施里的提权。
- 有的说是第三方依赖。
- 还有的归到遗留系统。
共同点藏在攻击目标里。Wiz 说,公开报告都在强调一件事。攻击者专门找存储的环境变量。尤其是能直接换来 AI 访问权限的密钥。
下游有 LLMJacking。说人话,就是把偷来的密钥拿去转卖模型额度。还有蒸馏需求在推着人买这些额度。蒸馏就是拿大模型的输出,去喂自己的小模型。
Wiz 说,没有哪一个漏洞或依赖能把这几起串起来。它们不是同一个团伙。但有一样很像。入口有扩展市场、构建系统、遗留服务。被盯上的,都是那串能换钱的密钥。
他们举了两个下游案例。厂商披露泄露后,30 分钟内就有人测试密钥。随后 30 小时里,它跑了约 80 万次 Bedrock 调用。Bedrock 是亚马逊的模型服务。另一个在 13 小时里跑了约 170 万次,超过 100 万次成功。按标价算,两起加起来可能超过 10 万美元。名单里的 Zeabur 已经因为这次事件宣布关停公司。
Cursor 这次坏的是一个包。和这九起放在一起看,丢的是同一类东西:能直接换模型额度的密钥。
我核了一遍自己的机器
公告出来后,我让脚本照着里面的命令跑了一遍检查。就在这台 Mac 上。
Cursor 的扩展列表里,Claude Code 是 2.1.27。VS Code 的扩展目录里,有 2.1.201 和 2.1.27 两个版本。
官方那条查后门的命令,终端回的是:No key found; machine not impacted。/.config/.smt、/.config/.smtk、~/Library/LaunchAgents/com.apple.sysmond.plist 也都不存在。
说实话,这不是我谨慎的结果。版本停在旧的地方,恰好没赶上那 11 个小时。要把这写成“我安全意识强”,是往自己脸上贴金。
还有一层得说清楚。这次核查是让脚本照着公告命令跑的。我没有一条条手敲。动作主体是这轮检查,结果能核。但不能写成我坐在电脑前,一行行排查的故事。
官方那条命令只查一把 key。文件有没有落下,还得自己看。
真要说收获,是那句“版本号看起来差不多”。2.1.27 和 2.1.313 之间隔着几百个版本,可我平时根本不会去数。风险也不会自己跳出来提醒你。
该改的几件小事
先核版本。Cursor 里打开扩展面板,搜 Claude Code,看版本号。命令行也能查:
1 | cursor --list-extensions --show-versions | grep anthropic.claude-code |
VS Code 用同样的命令,把 cursor 换成 code。前提是你装了它的命令行工具。
Cursor 在 X 上建议升到 2.1.314,博客里没写这个号。不在 312 和 313 里,就先不用折腾。
再查后门。macOS 上跑公告给的那条:
1 | grep -qs svc-telemetry ~/.ssh/authorized_keys && echo "svc-telemetry key found" || echo "No key found; machine not impacted" |
顺手确认 /.config/.smt、/.config/.smtk 和 ~/Library/LaunchAgents/com.apple.sysmond.plist 不存在。几样里中了一样,就按公告的处置走。
别只卸载。公告写得很直白。恶意代码会留下独立脚本,卸载扩展可能不够。
真命中了,先用官方脚本清持久化。再换一台可信的机器。把这台上能拿到的凭据,全部轮换一遍。GitHub token、云厂商密钥、模型 API key,一个都别漏。顺序别反。先换再清,等于把新凭据递进还开着的后门。
还有个更慢的动作。把高价值密钥从全局环境变量里挪走。Wiz 那九起里,攻击者翻的就是这层东西。能放项目级 .env 的,别塞进 shell 配置。能短期有效的,别发长期不过期的。这个动作今天做不完,但值得排进这周。
我还会继续装扩展
我不会因为这一次就不用扩展,也不会每次更新都去读 diff。成本太高,做不到。
我能改的,是看待更新的方式。扩展更新也会带来新代码。它更像一次部署,不像一次换皮肤。
装之前看一眼发布者。更新之后偶尔核一眼版本。出事了,知道去哪儿查就行。这几件事花不了几分钟。
代收点的盒子,你还是会拿。面单归面单,包裹归包裹,拆之前心里有数就行。
你上一次看扩展的版本号和发布者,是什么时候?今晚打开扩展面板,看一眼 Claude Code 那行,十秒。