给Claude Code会话逐一算内存账
MIT 开源工具 claude-load 按 Claude Code 会话归集机器负载,解决同名进程难以追溯归属的问题。作者首次运行发现15个会话共占约10.8GB内存,并定位到闲置会话和遗留 Python 进程。
AI 深度解读
开着十几个 Claude Code 会话,电脑变卡后,任务管理器却只给你一排同名的 node、claude、bash。作者做的 claude-load,解决的是一个具体问题:把 CPU 和内存占用归到对应会话,再找出会话关闭后仍在运行的开发进程。
首次运行,15 个会话合计占用 10.8 GB;清理后,整机已用内存从 35.2 GB 降到 31.2 GB。更值得程序员看的,是它如何识别进程归属、避免误杀,以及一个几乎全由 AI 编写的工具,为什么仍需要严格审查。
同名进程怎么归到具体会话
进程名分不出归属,但 Claude Code 留下了另一条线索:~/.claude/sessions/ 下,每个活跃会话都有一个 <pid>.json,包含 pid、sessionId、name、status、cwd 和 entrypoint。
claude-load 用会话 PID 作为起点,读取系统进程及其父进程 ID,再沿 PPID 链向上追溯。某个进程最终找到哪个会话,就把负载计入哪个会话。走过的链会缓存,避免重复遍历。
这让会话启动的 Vite、测试程序和 MCP server 也有了归属。作者发现,一个空闲会话仍占用约 0.5–0.7 GB,其中 claude 自身约 300–450 MB,另外还有每个会话各自启动的一组 Node MCP server。
会话没有继续工作,不代表它已经释放资源。
界面为每个会话展示 CPU、内存和六分钟曲线;不属于会话的进程则按名称合并,例如 chrome ×31。这样也能判断,卡顿是否真由 Claude 引起。

不过,这个会话注册表没有公开格式说明。工具只读取所需字段,并处理文件重写时的短暂异常;旁边存有令牌的 *.key 文件不会打开。这里用到的是内部实现线索,后续兼容性依赖 Claude Code 是否改变格式。图中内容也是演示数据,真实项目名没有公开。
清理按钮最难的部分,是确认自己没有杀错
第一版把「不属于会话、负载明显的开发进程」视为孤儿进程。审查后发现,活跃 PowerShell、IDE 辅助进程和 conhost 都可能被误判,按钮还会结束它们的整棵子进程树。
另一个漏洞更隐蔽:PID 会复用。界面展示的进程退出后,同一个 PID 可能已经分配给别的程序。如果仍按旧快照执行 taskkill /T,被结束的就是无关进程及其子进程。
新版先检查进程树根节点是否真的失去父进程。Windows 除了检查父 PID 是否存在,还比较创建时间,识别 PID 复用;macOS 和 Linux 则检查进程是否被 init、systemd 或 launchd 接管。
随后还要满足两项条件:树中包含真正的开发工具,且至少使用 0.3% CPU 或 150 MB 内存。只有 shell 不算;启动会话的终端和采样器自身也被排除。
结束前,工具重新获取快照,拒绝使用超过 15 秒的数据,并检查 PID 对应的进程名是否一致。会话进程和快照中不存在的 PID,不能从面板结束。
查出孤儿进程属于哪个仓库,还需要工作目录。Linux 读取 /proc/<pid>/cwd,macOS 使用 lsof;Windows 则通过 NtQueryInformationProcess 获取 PEB 地址,再用 ReadProcessMemory 读取,涉及 ProcessParameters 的 0x20 偏移和其中 CurrentDirectory 的 0x38 偏移。
这是只读操作,但作者也承认,杀毒软件或 EDR 可能拦截。企业开发机能否使用,不能只看功能截图判断。
十五个窗口共享采样,监控才不会拖慢电脑
如果每个会话都扫描一次系统,监控本身就会制造负载。claude-load 的做法是:整机只保留一个采样者,把结果写入 ~/.claude/state/load/snapshot.json,各会话每五秒读取一次。
作者在自己的 Windows 机器测得,Get-Process 耗时 76 ms,包含父子关系的完整 CIM 查询耗时 400 ms。因此,采样器每四秒运行一次较便宜的 Get-Process,只有出现新 PID 才查询 CIM,而且间隔不少于八秒。CPU 占比通过两次累计运行时间的差值计算。
每个会话每 30 秒更新一次 wanted 文件;三分钟无人更新,采样器自行退出。快照过期会触发重启,PID 文件配合命令行检查防止重复启动。作者给出的结果是:12 线程机器、15 个会话,监控约占 0.35% CPU 和 130 MB 内存。
macOS、Linux 则由某个会话持有文件租约并负责采样,15 秒不续约就由其他会话接管。Linux 的 %cpu 是进程整个生命周期的平均值,因此改用 time 差值;但该字段只有整秒精度,最终将采样间隔设为至少四秒,并禁止重叠执行,以减少假尖峰。
界面基于 Claude Code 2.1.287 引入的 mods:单个 TypeScript 模块通过 ($, e, next) 接入引擎,没有 Node 和 DOM,外部能力经由 $ 提供。终端使用 JSX 的 Box、Text、Button,桌面端还支持 Svg。CPU 超过 50% 或内存超过 85% 时,提示词上方会自动出现资源提示;/load 可以主动查看报告。

开发过程也暴露了平台约束:$ 只能传给同文件顶层函数,不能穿过 import;$.env.get 的变量名必须是字面量;Link 只允许 https;Box 没有 borderTop。这些限制会直接影响代码组织,不能照搬普通 Node 插件的写法。
我的判断
我认可它优先解决「资源归谁」的方向。任务管理器能看总量,按进程名分组也很常见,但面对多个仓库和 worktree,会话名称与进程树的关联更接近日常排查方式。代价是依赖未公开的注册表,以及不同系统的进程细节。
作者主要使用 Claude Code 的 Opus 5.5,在几天内完成工具,自己负责提需求和审查。主会话掌握架构,子代理分别修改不同文件,降低冲突。发布前的一轮 Opus 审查修复了九个局部缺陷,并逐个补测试,误判孤儿进程和 PID 复用都在其中。
这能说明审查有价值,却不能证明 AI 编码整体优于人工开发,原文没有对照数据。尤其是「确认后结束进程」这类操作,界面能点通远远不够。
测试也有边界。项目有 59 个测试,覆盖解析器、租约、过滤、结束确认,以及两种界面的八种语言;claude plugin test 能在真实引擎上模拟文件、进程、时钟和点击,还抓到了 claude plugin validate 漏掉的 $.env.get 问题。
但 macOS、Linux 尚未真机运行,只测试了录制的命令输出。Windows 上测试 Linux 分支,还遇到 /home/u 被宿主系统解析成 C:\home\u 的问题。模拟输入通过,不能替代目标系统上的实际验证。
清理效果同样要读准:15 个会话中归档了 12 个,包括八个 PR 已合并、四个被遗忘且没有 PR 的会话;整机内存减少 4 GB。不能据此推算每关闭一个会话固定省多少内存,也不能把首次统计的 10.8 GB 全当成可回收空间。
能拿来做什么
-
如果你经常同时运行多个仓库或 worktree,可以先用
/load找出空闲会话及其 Vite、测试和 MCP 子进程,再决定归档哪些。作者的清理入口会先请求确认,只处理获准对象,也启用了桌面端 PR 合并后自动归档。 -
如果要试用,先确认 Claude Code 为 2.1.287 或更新版本。下面两段分别解决 macOS、Linux、Git Bash,以及 PowerShell 的安装问题,选择对应的一段执行即可。
claude plugin marketplace add Gerrux/claude-load && claude plugin install claude-load@claude-load --config language=auto
claude plugin marketplace add Gerrux/claude-load; if ($?) { claude plugin install claude-load@claude-load --config language=auto }
注意第二段用 if ($?) 判断前一步成功后才安装。桌面端也可通过「+ → Plugins → Add marketplace → Gerrux/claude-load → Add plugin」添加,再运行 /reload-plugins 和 /load。严格的 PowerShell AllSigned 或 Constrained Language Mode 策略会阻止采样器启动。
- 如果你正在让 AI 编写 Node 开发工具,尤其涉及结束进程、启动后台服务,可以把审查重点放在状态过期、PID 复用、路径转义和并发重入上。作者遇到的
C:\Users\O'Brien路径就曾破坏启动命令,这类边界比界面是否漂亮更值得先验证。