claude-code-gc: removing old Claude Code versions

A small Linux tool that lists the Claude Code versions that updates leave on disk, shows which ones running processes still use, and removes the rest.

The problem

Claude Code updates itself often, and every update leaves the previous version on disk. On a remote development machine the same version is usually stored up to three times: the CLI binary in ~/.local/share/claude/versions/, the editor extension in ~/.vscode-server/extensions/, and the downloaded VSIX file in the extension cache. Each copy is 250 to 290 MB, so a small VPS fills up within a few weeks.

The old copies can be deleted by hand, but each directory has to be checked first: a session started days ago may still run an older binary, and the editor extension runs from its own versioned directory.

How it works

claude-code-gc scans a fixed list of directories. CLI versions come from ~/.local/share/claude/versions/. Extensions come from the extension directories of VS Code, Cursor and Windsurf, and VSIX files from the two VS Code download caches. In the extension and VSIX directories it only considers entries named anthropic.claude-code-<version>....

It then reads /proc. A version counts as in use when a running process has it as its executable (/proc/<pid>/exe) or names a file inside it on its command line. The second case covers the VS Code extension, which runs as node .../extension.js. Every version in use is kept, and so is the newest version of each kind (cli, extension, vsix). --keep N keeps the newest N versions per kind, and --keep 0 keeps only what is in use.

The default is a dry run. This is the example from the README, taken on a VPS with several sessions open:

$ claude-code-gc
cli        2.1.299     253.0 MB  in use (pid 324791)    ~/.local/share/claude/versions/2.1.299
cli        2.1.300     253.8 MB  remove                 ~/.local/share/claude/versions/2.1.300
cli        2.1.302     272.6 MB  in use (pid 1683736)   ~/.local/share/claude/versions/2.1.302
extension  2.1.300     266.9 MB  remove                 ~/.vscode-server/extensions/anthropic.claude-code-2.1.300-linux-x64
extension  2.1.301     267.5 MB  keep (newest)          ~/.vscode-server/extensions/anthropic.claude-code-2.1.301-linux-x64

2 item(s) removable, 520.7 MB. Run with --delete to remove them.
note: pid 3581507 still runs deleted ~/.local/share/claude/versions/2.1.292; its space returns when it exits.

--delete removes the items marked remove. The note lines list long-running sessions that still execute a binary that was already deleted. Linux frees that space only when the process exits, so ending old sessions is the only way to get it back.

The tool needs Python 3.10 or newer and has no dependencies.

Testing

The tests build a fake home directory with three CLI versions, two extension versions and one unrelated extension, plus a fake /proc with exe symlinks and cmdline files. They check that other extensions are ignored, that the newest and the in-use versions are kept, and that an extension counts as in use through its command line. One test makes sure that a process running 2.1.301 does not mark the directory 2.1.30 as in use. Others cover the report of a deleted binary that is still running, a dry run followed by --delete, and --keep 0.

There are 8 tests. CI runs them on Python 3.10, 3.11, 3.12 and 3.13, together with ruff check and ruff format --check, and runs the command once on the runner.

Limitations

  • It runs on Linux only, because it reads /proc to find running processes.
  • It scans only the directories listed in the README. Installations in other places are not found.
  • Space held by a process that still runs a deleted binary cannot be freed by the tool. It only reports these processes.

The code and installation instructions are at github.com/Jwrede/claude-code-gc.