Claude Code 误删文件的恢复与防护实测
作者测试了 Claude Code 文件历史、Git 和编辑器本地历史等恢复路径,指出 /rewind 无法撤销单纯由 shell 删除的文件。文章还用 18 条命令测试防护钩子,揭示命令匹配规则可能漏掉脚本内部的删除操作。
AI 深度解读
Claude Code 删掉文件后,/rewind 未必能救回来。它恢复的是特定编辑工具留下的检查点,不是整个磁盘的历史。作者逐一测试了检查点副本、Git 和编辑器本地历史,结论是:能否恢复,取决于删除前有没有其他副本。
更值得程序员关注的是事故怎么发生。危险操作可能藏在测试、构建脚本和子代理生成的代码里,外层只显示一次正常的执行命令。限制命令文本、限制进程权限、保存可恢复副本,解决的是三个不同问题。
文件刚被删,先停止写入,再判断副本在哪里
作者建议先按 Esc 中断,或用 Ctrl+C 退出,暂时不要让 Claude 重建文件。重建会产生写入,可能覆盖恢复工具需要的磁盘块。原文引用的一起事故中,删除过程只用了 103 秒,最终净损失 48,218 个文件。
Shell 删除通常绕过回收站。macOS、Linux 和 Git Bash 的 rm,以及 PowerShell 的 Remove-Item,都不能指望去废纸篓里找回来。
恢复顺序可以沿着副本来源走:先试 /rewind,再查 ~/.claude/file-history/、Git、编辑器本地历史,最后检查备份。
/rewind 只覆盖 Claude 用 Edit、Write、NotebookEdit 修改过的文件,以及这些文件后续发生的 Shell 改动。一个从未被这些工具编辑、只被 rm 删除的文件,没有对应检查点。后台子代理的编辑也不在恢复范围内,符号链接和硬链接文件会被跳过。
空输入时连按两次 Esc 也能进入恢复菜单。Restore code 保留对话,Restore code and conversation 同时恢复代码和对话;如果只有 Restore conversation,通常说明该检查点没有可恢复的文件变更。
检查点默认约 30 天后会被清理,cleanupPeriodDays 可以调整保留时间。菜单失效时,还可以直接查找普通文件副本:
grep -rl "a line you remember from the lost file" ~/.claude/file-history/
关键是搜索范围 ~/.claude/file-history/:它不是整个项目的备份。副本位于 <session-id> 子目录,名称类似 1d9a83bb87b6a918@v2,同一哈希下最大的 @vN 是最新版本。作者检查时看到了 40 个会话、39 MB 快照,并验证过其中一份除换行符外与原文件一致。
Git 则要区分状态。已提交文件可以从提交恢复;暂存过但没提交的内容,可能仍在索引或对象库中。git fsck --lost-found 能把找到的孤立对象写入 .git/lost-found/other/,但通常丢失文件名,需要按内容辨认。它不能找回从未进入 Git 对象库的任意未跟踪文件。
遇到 git reset --hard HEAD~2,作者实测可以通过 git reflog 找回提交,再用 git reset --hard 'HEAD@{1}' 恢复。这个命令也会覆盖当前工作区,必须先确认目标和现有改动。
如果 .git 一起被删,本地 Git 就帮不上忙了。未跟踪文件可以试 VS Code 的 Local History: Find Entry to Restore,或 JetBrains 的 Local History → Show History。数据库则依赖服务商的时间点恢复或自己的导出备份。
为什么拦住 rm,仍然挡不住测试删掉主目录
命令审查只能检查入口,不能保证程序运行后的行为。
原文引用的 issue #105342 发生在 Claude Code 2.1.311:子代理使用 isolation: "worktree",却在测试中把 20; rm -rf ~ 作为参数传给 Shell fixture。外层执行的是 cargo test,真正的删除命令没有出现在工具调用文本中。测试使用真实 $HOME,约六分钟后被停止时,多个项目和 ~/.config 已遭删除。
Git worktree 只是另一份检出目录,不会改变进程能访问哪些文件。
类似风险也不限于删除。issue #104156 中,Node 脚本把占位 PID -1 传给 kill(-1, SIGKILL),杀掉了该用户拥有的进程,包括其他 Claude Code 会话。
几种保护的差别,原文用这张图做了对照:

Bash(rm *) 这样的规则匹配命令文本,原文列出的 /bin/rm -rf build/、bash -c 'rm -rf build/' 就可能绕开它。内置关键路径检查能识别部分针对 /、主目录、磁盘和工作目录的删除,但同样看不到脚本内部。
PreToolUse hook 可以表达更复杂的条件,例如允许清理 node_modules、dist、.next,拦截其他递归删除。作者用 18 条命令测试过自己的 Node hook,不过输入只包含工具调用 JSON,它仍然无法检查 cargo test 内部的删除。
Bash sandbox 由操作系统约束,能覆盖测试运行器、构建脚本和 Node 子进程。默认允许写入工作目录、临时目录和额外放行目录。它限制损失范围,却保不住项目内部被误删的文件。
配置要分别覆盖 Shell 和文件编辑工具
作者检查范围截至 2026 年 10 月 30 日、Claude Code 2.1.314。恢复命令和 hook 的实测环境是 Windows 11、Git Bash、Git 2.54。
下面这份原文配置,把命令确认、文件工具边界和 Shell sandbox 放在一起,保存到 ~/.claude/settings.json:
{
"permissions": {
"ask": [
"Bash(rm *)",
"Bash(git reset *)",
"Bash(git clean *)",
"Bash(git push --force *)"
],
"deny": ["Read(./.env)", "Read(./.env.*)"],
"blockWritesOutsideWorkingDirectories": true
},
"sandbox": {
"enabled": true,
"allowUnsandboxedCommands": false
}
}
这里最需要核对的是 blockWritesOutsideWorkingDirectories 和 allowUnsandboxedCommands 两行。前者要求 2.1.314+,只约束 Write、Edit、NotebookEdit;后者关闭命令失败后转到 sandbox 外重试的出口。作者提醒,当时设置参考页还只记录了读取侧的 blockReadsOutsideWorkingDirectories,所以应先运行 claude --version。
ask 让合法清理仍有人工确认入口,也会在 auto 模式下提示,并优先于更宽泛的允许规则。Read 拒绝规则同时限制同一路径的编辑和写入,但不能据此认定所有 Shell 程序都读不到凭据。
平台也有前提:Bash sandbox 支持 macOS、Linux 和 WSL2,不支持原生 Windows。Windows 用户需要 WSL2 或 dev container 才能获得这一层保护。原生 PowerShell 虽有关键路径检查,2.1.283 起还覆盖部分 cmd /c rd、rmdir、del、erase,但这些仍不等同于进程隔离。
我的判断
作者说得最对的地方,是把「回滚能力」和「权限边界」分开了。/rewind 适合撤销部分编辑,Git 负责保存版本,sandbox 控制程序可触达的范围,任何一项都不能替代其余两项。
证据也要分层看。检查点副本、Git 恢复路径和 18 条 hook 命令是作者实测;严重事故来自外部报道和 issue。原文没有提供完整的 18 条测试结果表,也没有团队长期对照数据,因此不能把这个 hook 当作经过充分验证的安全方案。
正则 hook 适合减少常见误操作,难以完整理解 Shell 引号、变量展开和间接调用。它的价值是增加一次拦截机会。需要硬性边界时,容器、VM 或受限系统用户更合适,但挂载目录仍可被删除,备份也不能和生产资源共用可删除它们的凭据。
--dangerously-skip-permissions 会跳过大量确认;2.1.311+ 的 CLAUDE_CODE_EVEN_MORE_DANGEROUSLY_SKIP_PERMISSIONS=1 连关键路径检查也能关闭。作者建议仅在可丢弃的容器或 VM 中使用,有明确理由。
能拿来做什么
- 让 AI 长时间修改前端或 Node 项目前,先检查工作区并提交、推送需要保留的内容。远端副本能应对本地
.git被一起删除,未推送的工作仍需另存。 - 检查项目中的清理脚本和测试夹具,尤其是拼接 Shell 参数、遍历链接目录的代码。测试里的
HOME应指向临时目录,避免一个~落到真实主目录。 - 按平台启用 sandbox,并为 Claude 文件工具配置工作目录外写入限制。不要把
isolation: "worktree"当作安全隔离,也不要只靠Bash(rm *)。 - 把恢复入口提前记下来:检查点目录、编辑器本地历史和独立备份位置。发生误删时先停止写入,再查副本,避免立刻让 AI 重建。