Problem
~/.vscode-server on a Coder workspace grows unbounded (11 GB observed at
investigation time; exact composition drifts, verify current state before
acting on old numbers): interrupted cli/servers/*.staging downloads,
cli/servers/Stable-* directories the CLI no longer considers live,
code-<commit> binaries with no matching server directory, and superseded
extension versions still on disk under extensions/. This inflates the
dentry/inode slab on top of wasting home-volume space.
Separately: orphaned dbus-daemon --session processes accumulate over days,
ppid == 1, leaking from dbus-launch --autolaunch firing whenever
something touches libsecret with no session bus available. Unrelated to VS
Code's own growth, found during the same investigation.
What's needed
~/.vscode-server GC — lives in ppat/coder, not here
Originally scoped to this repo as private_dot_local/bin/executable_vscode-server-gc
on the reasoning that it's "personal state operating on a personal
directory." That reasoning doesn't hold: ~/.vscode-server is created by VS
Code the moment it connects to a workspace, independent of whether dotfiles
have ever been applied there — a workspace with no dotfiles applied still
accumulates it (confirmed: the test Coder workspace hit ~11 GB with
dotfiles never applied). A dotfiles-owned script silently no-ops on every
workspace where dotfiles haven't landed, and the existing scheduler
(coder_script.vscode_server_gc in ppat/coder's
templates/kubernetes/homelab-workspace/scripts.tf) was written with a
[ -x ... ] || true guard that swallows exactly that failure into an
apparent success.
Corrected shape, implemented in ppat/coder: script-vscode-server-gc.sh
lives in the template directory alongside script-agent-startup.sh /
script-memory-watchdog.sh, is mounted into the pod via
configmap.tf/deployment.tf, and is invoked directly by the existing
weekly coder_script cron with no existence-check guard — a failure now
surfaces as a failed run in the Coder UI instead of a silent no-op.
Deletion signals (unchanged from the original plan, each driven by
something VS Code already writes to disk, not a version-number guess):
cli/servers/*.staging — suffix alone (always an interrupted download)
cli/servers/Stable-<hash> — not listed in cli/servers/lru.json
code-<hash> CLI binaries — no matching cli/servers/Stable-<hash> remains
extensions/<name> — listed in extensions/.obsolete and not referenced by extensions/extensions.json
data/logs/* is deliberately not cleaned (dropped from the original
plan's "older than 7 days" idea) — nothing on disk marks a dated log
directory as safe to remove, so there's no disk-based signal to drive that
deletion the way there is for the other four classes.
dbus orphan fix — lives in ppat/coder, image only
No cleanup for existing orphans (a pod restart already clears them).
Durable fix: DBUS_SESSION_BUS_ADDRESS=disabled: added to
images/homelab-workspace/Dockerfile's /etc/environment block — a
universal, stable fact about this image (it has no session bus and never
will). Verified on the disposable test workspace that disabled: makes
both the GDBus and raw libdbus connection paths fail in <5ms with no
daemon spawned, instead of attempting autolaunch.
Acceptance criteria
Related
Problem
~/.vscode-serveron a Coder workspace grows unbounded (11 GB observed atinvestigation time; exact composition drifts, verify current state before
acting on old numbers): interrupted
cli/servers/*.stagingdownloads,cli/servers/Stable-*directories the CLI no longer considers live,code-<commit>binaries with no matching server directory, and supersededextension versions still on disk under
extensions/. This inflates thedentry/inode slab on top of wasting home-volume space.
Separately: orphaned
dbus-daemon --sessionprocesses accumulate over days,ppid == 1, leaking fromdbus-launch --autolaunchfiring wheneversomething touches libsecret with no session bus available. Unrelated to VS
Code's own growth, found during the same investigation.
What's needed
~/.vscode-serverGC — lives inppat/coder, not hereOriginally scoped to this repo as
private_dot_local/bin/executable_vscode-server-gcon the reasoning that it's "personal state operating on a personal
directory." That reasoning doesn't hold:
~/.vscode-serveris created by VSCode the moment it connects to a workspace, independent of whether dotfiles
have ever been applied there — a workspace with no dotfiles applied still
accumulates it (confirmed: the
testCoder workspace hit ~11 GB withdotfiles never applied). A dotfiles-owned script silently no-ops on every
workspace where dotfiles haven't landed, and the existing scheduler
(
coder_script.vscode_server_gcinppat/coder'stemplates/kubernetes/homelab-workspace/scripts.tf) was written with a[ -x ... ] || trueguard that swallows exactly that failure into anapparent success.
Corrected shape, implemented in
ppat/coder:script-vscode-server-gc.shlives in the template directory alongside
script-agent-startup.sh/script-memory-watchdog.sh, is mounted into the pod viaconfigmap.tf/deployment.tf, and is invoked directly by the existingweekly
coder_scriptcron with no existence-check guard — a failure nowsurfaces as a failed run in the Coder UI instead of a silent no-op.
Deletion signals (unchanged from the original plan, each driven by
something VS Code already writes to disk, not a version-number guess):
cli/servers/*.staging— suffix alone (always an interrupted download)cli/servers/Stable-<hash>— not listed incli/servers/lru.jsoncode-<hash>CLI binaries — no matchingcli/servers/Stable-<hash>remainsextensions/<name>— listed inextensions/.obsoleteand not referenced byextensions/extensions.jsondata/logs/*is deliberately not cleaned (dropped from the originalplan's "older than 7 days" idea) — nothing on disk marks a dated log
directory as safe to remove, so there's no disk-based signal to drive that
deletion the way there is for the other four classes.
dbus orphan fix — lives in
ppat/coder, image onlyNo cleanup for existing orphans (a pod restart already clears them).
Durable fix:
DBUS_SESSION_BUS_ADDRESS=disabled:added toimages/homelab-workspace/Dockerfile's/etc/environmentblock — auniversal, stable fact about this image (it has no session bus and never
will). Verified on the disposable
testworkspace thatdisabled:makesboth the GDBus and raw libdbus connection paths fail in <5ms with no
daemon spawned, instead of attempting autolaunch.
Acceptance criteria
script-vscode-server-gc.shadded toppat/coder's template,mounted via ConfigMap, invoked directly by the existing cron (no
dotfiles dependency, no existence-check guard).
~/code/roo-history/(and anything outside~/.vscode-server)unaffected — the script has a root-dir sanity check and only ever
operates under the path it's given.
testworkspace: a real (non-dry-run) runfreed space and the still-"live" (per
lru.json) server directoryremained present and functional afterwards (
code-server --versionran successfully post-GC) — reconnecting re-downloads nothing.
DBUS_SESSION_BUS_ADDRESS=disabled:added to the image; confirmed ontestthat it suppresses autolaunch (no daemon spawned) rather thanproducing an error class any libsecret-using tool doesn't already
handle.
pre-commit run --all-filespasses inppat/coder.Related
ppat/coder.