Skip to content

Reap abandoned build volumes and clarify stale-volume errors#178

Merged
jetm merged 4 commits into
mainfrom
jtia/reap-abandoned-avo-volumes
Jul 13, 2026
Merged

Reap abandoned build volumes and clarify stale-volume errors#178
jetm merged 4 commits into
mainfrom
jtia/reap-abandoned-avo-volumes

Conversation

@jetm

@jetm jetm commented Jul 8, 2026

Copy link
Copy Markdown
Contributor

Problem

Each project gets a per-project Docker volume (avo-<uuid>) recorded in its .avocado-state file. Deleting a project directory by hand drops the folder but not the volume, so avo-* volumes accumulate unbounded. Worse, a stale or half-populated volume makes avocado build fail during runtime build dev with a cryptic grep: .../rootfs-work/etc/passwd: No such file, naming neither the cause nor the fix.

Solution

Reclaim provably-abandoned avo-* volumes at the moment a fresh volume is minted, and guard the rootfs build so a half-populated sysroot fails fast with an actionable message instead of the grep noise.

Key changes

  • Auto-reap abandoned avo-* volumes in get_or_create_volume (the natural GC point, and the only path already holding a container-tool handle, so init and the pure-filesystem commands stay docker-free). Best-effort: a daemon-down or held-volume failure is swallowed and never blocks a build.
  • Share one classifier, avo_abandonment_reason, between the reap and avocado prune so the two paths cannot drift on what "abandoned" means.
  • Guard the rootfs build: if rootfs-work lacks /etc/passwd after the sysroot copy, exit with a message pointing at avocado clean and avocado prune.
  • Tests: 5 classifier cases plus generated-script assertions (guard present and ordered before user creation).

Reviewer notes

  • Behavior change: install/build now delete provably-dead avo-* volumes (source dir gone, no .avocado-state, or state pointing at a different volume). Active project volumes are never touched.
  • Verified against the QEMU getting-started flow: a clean build still succeeds, and the guard fires with the actionable message on a simulated half-populated sysroot.
  • Companion docs troubleshooting note is a separate peridio/docs PR.

jetm added 2 commits July 8, 2026 09:28
Each project gets a per-project docker volume (avo-<uuid>) recorded in
its .avocado-state file. Deleting the project directory by hand drops
the folder but not the volume, so the volumes pile up unbounded: nothing
reclaimed them short of a user knowing to run `avocado prune`.

Sweep provably-abandoned avo-* volumes at the moment a fresh volume is
minted in get_or_create_volume. That is the natural GC point (a new
project is starting) and the only path already holding a container-tool
handle, so init and the other pure-filesystem commands stay docker-free.
The sweep is best-effort: a daemon-down or held-volume failure is
swallowed so it can never block a build. Reuse a single classifier,
avo_abandonment_reason, from both the reap and `avocado prune` so the two
paths cannot drift on what "abandoned" means.
The rootfs build copies the sysroot into rootfs-work and immediately
runs the user-creation step, which greps /etc/passwd. When a build
volume is stale or a prior install was interrupted, the sysroot can
carry /usr but not /etc/passwd; the copy then also lacks it, and the
user surfaced a cryptic `grep: .../rootfs-work/etc/passwd: No such
file` with no hint at the cause or the fix.

Check for the base rootfs /etc/passwd right after the copy, before the
user-creation step, and exit with a message that names the stale-volume
cause and the recovery. Point at both `avocado clean` and `avocado
prune`: clean drops the active project's volume, but a reporter found
clean alone insufficient and needed prune to clear an abandoned volume
that was shadowing the build.

Signed-off-by: Javier Tia <javier@peridio.com>
@jetm

jetm commented Jul 10, 2026

Copy link
Copy Markdown
Contributor Author

@lee-reinhardt could you take a look at this one when you get a chance?

Comment thread src/utils/volume.rs Outdated
Comment thread src/utils/volume.rs
Comment thread src/utils/volume.rs Outdated
Comment thread src/utils/volume.rs
jetm added 2 commits July 13, 2026 12:30
rust 1.97 stable tightened several default lints, so `cargo clippy -D
warnings` (run by the pre-commit hook and CI) started failing on code
untouched by this branch, blocking every commit and PR in the repo.

Fix them mechanically with no behavior change: drop redundant references
in format arguments (connect keys list, ext image, upgrade), iterate a
map with values_mut() instead of discarding the key (sdk deps), and
collapse a match-that-returns-None into the ? operator (config path
lookup).

Signed-off-by: Javier Tia <javier@peridio.com>
Address review feedback on the reap added earlier in this branch.

inspect_source_path_label now returns Result<Option<String>>: a failed
`docker volume inspect` (daemon hiccup, timeout, unparseable output) is
an Err the reap skips, instead of collapsing to None and being read as
"no source_path label", which classified the volume as abandoned and
deleted an active project's volume on a transient failure.

Persist .avocado-state before creating the docker volume in
get_or_create_volume. This closes a cross-process race: a concurrent
reap in another project could otherwise observe a freshly created volume
in the window before its state file exists, classify it as abandoned,
and delete it mid-mint. Writing state first means the volume is never
visible without its pointer, and volume_exists already tolerates a state
file that points at a not-yet-created volume.

Print each reaped volume and its reason under --verbose so a surprising
deletion can be diagnosed, matching prune's per-volume output. Add the
CHANGELOG entry for the user-visible auto-reap behavior.

Signed-off-by: Javier Tia <javier@peridio.com>
@jetm

jetm commented Jul 13, 2026

Copy link
Copy Markdown
Contributor Author

Pushed two commits: e3acc63 addresses all four review points, and 2a11f58 fixes clippy lints that rust 1.97 started flagging repo-wide (redundant format refs, a for (_, v) map iter, a match?). That second one is unrelated to this PR's feature, but cargo clippy -D warnings was failing the pre-commit hook and CI on untouched files, so I folded the mechanical fix in here to unblock. Happy to split it into its own PR if you'd rather keep this one focused.

@jetm
jetm requested a review from lee-reinhardt July 13, 2026 18:34
@jetm

jetm commented Jul 13, 2026

Copy link
Copy Markdown
Contributor Author

All four review points are addressed in e3acc63 (per-thread replies above), and CI is green across the board — Test Suite, qemux86-64 build, Security Audit, Windows check, and CodeQL. Ready for another look whenever you have a moment.

@jetm
jetm merged commit abd5221 into main Jul 13, 2026
8 checks passed
@jetm
jetm deleted the jtia/reap-abandoned-avo-volumes branch July 13, 2026 20:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants