编译 | 苏宓
出品 | CSDN(ID:CSDNnews)
“两次 CPU 飙升的背后有个巧合,那就是——‘我们 CEO 登录了账号。’于是,我们把 CEO 的账号给封了,继续排查原因......”
听起来像段子,但这真是 Sketch.dev 的工程师亲口写下的“事故总结”。而这一切的起因,只是因为一段由 AI 生成的代码。
Sketch.dev 是一家用 AI 辅助程序员写代码的开发平台,他们甚至用自己的工具开发自家产品。但在 7 月中旬,他们「栽」在了自己信任的 AI 手里。

系统突然卡顿、服务变慢、CPU 飙升,接连几次“迷你宕机”之后,团队发现:每次崩溃的起点,都是 CEO 登录系统。他们当机立断地封了 CEO 的账号,问题果然暂时消失了。
但后来经过排查,问题不在 CEO,而在代码。
对此,7 月 31 日,Sketch.dev 工程师 Josh Bleecher Snyder 和 Sean McCullough 发布了一篇博客——《我们第一次因 LLM 生成代码而宕机》,对整个事件进行了回顾总结。这不是模型瞎写代码的问题,而是看起来没问题的 AI 重构,把一个逻辑错误埋进了系统底层。

这次事故,成了团队第一次真正感受到:AI 编码代理,也会带来隐形的生产风险——不是“不会写”,而是“写得像对的”。
起因
时间回到 7 月 15 日,Sketch.dev 的工程团队发现自家网站开始出现一连串的小范围宕机。
一开始的部署看起来很正常,但没过多久,CPU 占用飙升,系统响应开始严重卡顿。
后台的性能分析工具显示,是一些极其复杂的 SQL 查询在疯狂执行全表扫描,系统已经被拖到快撑不住的临界点。
为了解决这种情况,彼时 Sketch.dev 的工程师觉得,无论如何,这些查询都必须进行优化或彻底重写。于是,团队修改了查询逻辑并重新部署。没想到同样的情况再次发生:最初一切正常,之后又逐步滑向性能崩溃,陷入了恶性循环。
进一步分析后,他们惊讶地发现,两次 CPU 飙升背后的“触发器”竟然是:“我们 CEO 登录了。”
于是他们决定再次重启部署清理状态,并顺手永久封了 CEO 的账号,继续追查问题。
虽然性能分析工具依然显示是数据库资源争用的问题,但工程师们觉得,这个解释已经站不住脚了。
他们继续往上追查调用栈,结果发现有一段平时几乎不会执行的代码路径,正是引发这些“数据库过载查询”的根源。而这段代码——最近才刚被重构过。
于是,他们果断撤回了那次重构,重新部署了代码,也把被封号的 CEO 解封,然后开始深入分析到底哪里出了问题。
直接原因初解析
根据 Sketch.dev 工程团队的介绍,其日常会使用自家 AI 平台来开发 Sketch 这款产品,而此次问题的根源在于一段由 LLM 生成、随后经人工审核的大规模代码重构。
这段代码被从一个文件移动到另一个文件中,而 Bug 就悄然藏在这个过程中。
详细来看,重构前的代码如下:
for {
repos, repoResp, err := ghClient.Apps.ListUserRepos(ctx, *installation.ID, repoOpt)
if err != nil {
// Log error but continue with other installations
log.Printf("Error fetching repositories for installation %d: %v", *installation.ID, err)
break
}
// ...
}
重构后的代码:
for {
repos, repoResp, err := ghClient.ListUserRepos(ctx, *installation.ID, repoOpt)
if err != nil {
// Log error but continue with other installations
log.Printf("Error fetching repositories for installation %d: %v", *installation.ID, err)
continue
}
// ...
}
原本的 break 被改成了 continue,错误被“静默”处理,直接导致死循环。
根本原因
说白了,这次宕机事故,其实源于一次代码迁移时的一个细微变更。但因为整段代码整体都在迁移,这个小变动就被“淹没”在大量修改里,开发团队在代码审核时没能察觉。
该团队指出,这暴露出整个行业在“识别代码小幅变更”这方面工具的不足。像 Git 这样的主流工具,确实可以识别一个文件整体的“迁移+改动”,但要是在同一个文件中某段代码被改动了位置又稍作修改,它就很难看出——技术上实现起来也确实不简单。
在实际开发中,这种情况并不少见:一大片红绿 diff(即“新增/删改”的代码差异)中看起来大同小异,很容易漏掉真正重要的改动。而这种错误,并不是因为用了 AI 才出现,哪怕是人类开发者也可能踩坑。
但问题在于:AI 更容易犯这种错。
人类开发者做重构时,往往是直接剪切原来的代码,再粘贴到新位置,然后做有意识的修改。这个过程相对“闭环”,出错概率比较低。
然而,AI 编码助手的逻辑则不同——它不会“剪切粘贴”,而是“先删掉一段代码,再重新写一段”。本质上,它是在尝试“转录”旧的逻辑到新位置,稍有偏差就可能抄错。
而这次的 Bug,就属于这种“转录错误”的典型案例。
对此,Sketch.dev 也举了一个典型例子来说明这种转录错误是如何发生的:
if err != nil {
// Log error but continue with other installations
log.Printf("Error fetching repositories for installation %d: %v", *installation.ID, err)
break
}
可以看到,上面代码的注释写的是“but continue”,但实际的程序逻辑却写成了“中断执行”(break)。也就是说,注释和代码本身“打架”了。
这种错误,是怎么发生的?该团队工程师分析后发现,这是 AI 在生成代码时两种“判断信号”发生了冲突:
- 一种是“转录信号”,也就是它试图照搬旧代码中的逻辑(这一层面它想用 break);
- 另一种是“局部预测”,也就是它根据上下文猜测此时该写什么(这一层面它认为应该用 continue)。
很不幸,这次 AI 更相信自己的“直觉”——结果它选择了 continue,也就是错误的那个选项,从而引发了 Bug。
预防措施
为避免类似问题再次发生,Sketch.dev 研发团队对平台的代理执行环境进行了改进,新增了剪贴板支持功能。现在,AI 代理在修改文件时可以将代码复制到剪贴板,并从中读取内容。
为了避免类似的错误再次发生,Sketch.dev 研发团队给他们的 AI 编码环境增加了“剪贴板”功能。现在,AI 在修改代码时,可以像人一样复制粘贴代码,这样可以尽量保持原样不出错。
不过问题也来了——比如在像 Python 这样非常依赖缩进的语言里,粘贴过去的代码缩进可能不对,所以他们还加了一个“自动调整缩进”的机制,确保粘贴后的代码格式不会乱。未来他们还打算接入更智能的代码格式工具(LSP),让粘贴缩进这件事更自动化。
虽然这个新功能刚上线不久,但在一些更强大的 AI 模型上,初步效果还不错。
此外,该团队也呼吁:Git 能支持更智能的“跨区域改动检测”功能。这个技术本来就有用,但在现在这个“越来越多代码由 AI 生成”的时代,如果 Git 能识别某段代码从 A 文件移动到 B 文件,还能看出其中有没有被悄悄改动,将会极大提升发现错误的能力。
AI 编程失误引发问题不止一次两次了
时下,Sketch.dev 的经历,也引发了广泛关注。因为 AI 生成的代码导致网站宕机,工程师却在第一时间将“矛头”首先对准自家 CEO,还直接封禁了他的账户。虽然事后澄清是误会,但仍引发大量网友吐槽:
“CEO 何其的冤枉,他就只是登录时间碰巧和故障撞上了,然后你们居然把他封号了?”
但这场“乌龙”只是当下 AI 编程困境的缩影,类似的情况早已不是孤例。
像不久前我们报道的——SaaStr 创始人 Jason Lemkin 就曾因使用 AI 编程工具 Replit 而头痛不已:AI 不仅多次无视指令、篡改测试数据,甚至在他反复强调“不要动线上数据库”的情况下,仍然一键删库。气得他发文吐槽:
“我提醒了它整整 11 次,但没用……我现在真的开始担心 AI 失控了。”

无独有偶,Google 的 Gemini CLI 工具也出过同样的事故。一位产品经理尝试用它整理文件夹,结果 AI 误把文件移到了一个根本不存在的目录,数据直接清空。出事之后, Gemini CLI 工具还自动“认错”道:
“我彻底而灾难性地失败了。命令审查显示我严重不称职。”
同样就在两天前,更有开发者在 Reddit 论坛中发帖警告称:“Gemini CLI 删除了我的整个 Windows 系统”,让人觉得 AI 现在在帮助人类处理技术问题时逐渐离谱。

这名开发者写道:
我分享这个经历,是想提醒所有使用 Gemini CLI 或类似工具、涉及文件系统操作的用户:一定要小心。
当时我在 Windows 上使用 Gemini CLI(从 Git Bash 启动,在项目根目录),我让它把我的项目用另一种技术重写,并新建一个分支。本来它应该只删除当前分支下的文件,但结果却执行了一个破坏性的 rm -rf 命令。
尽管有些删除操作因为权限问题(比如 C:\ 等系统文件夹)失败了,但它仍然把我整个 C 盘的大量内容都删掉了。
任务结束后,我的系统几乎彻底崩了:
- 程序无法启动
- 资源管理器打不开
- 很多关键文件和应用全都不见了
幸运的是,我通过系统还原(rstrui)挽回了大约 90% 的系统数据,但依然有不少程序丢失或损坏。
补充说明:我还贴出了日志证据,包括:

向 Gemini CLI 发出的提示内容,其中有确认是否可以删除当前分支文件(但我没法找回 Gemini 返回的确认消息,因为我是用 Gmail 登录的,不是 API key)

Git 日志:确认我在新建分支上操作,随后文件被删除

renderer.log:记录了删除文件的操作

filewatcher.log:进一步确认文件被删除

系统还原日志

使用 Wise Data Recovery 工具识别出的丢失文件
这些问题背后,其实都是同一种现象在作祟:AI 模型有时候并不真正“理解”代码,这种方式往往会产生听起来“像是真的”但实际上完全错误的结果。
在 Stack Overflow 最新发布的开发者调查中,66% 的开发者就表示,他们经常遇到 AI 输出“差一点就对”的答案,而调试这些“似是而非”的代码反而更花时间,45% 的人对此深有同感。

相比之下,真正对 AI 工具“完全放心”的人寥寥无几——只有 3% 的受访者表示“高度信任”,而明确“不信”的人更多,高达 46%。

经验越丰富的程序员,态度往往也越谨慎:只有 2.5% 的资深开发者“高度信任”AI,反倒有 20.7% 明确表示“高度不信任”。

正如有网友所说:“写代码变成了喂提示词 + 修烂摊子,AI 编程的未来也许值得期待,但现在还远没到可以闭眼上产线的阶段。”
对此,你怎么看?
参考:
https://sketch.dev/blog/our-first-outage-from-llm-written-code
https://www.reddit.com/r/GeminiAI/comments/1md2quz/warning_gemini_cli_deleted_my_entire_windows/