ref:main

feat(runner): cross-worker build-state portability — same-host (#312) #29

open colechristensen cole.christensen@gmail.com wants to merge feat/312-cross-worker-build-state into main

Part of fangorn/anvil#312 — the runner (data-plane) half. The server half is fangorn/anvil#177 (branch feat/312-cross-worker-build-state).

What & why

Makes prerequisite CI build state follow the job across parallel slots on one host, instead of being trapped in the slot that produced it. All slots share one Docker daemon, so the local image store is the shared medium — no network.

  • runner/image_transfer.rs (new):
    • snapshot_local — after a job passes, layer the workspace onto the prepared image (docker create + cp + commitanvil-run-<run>:<job>), committed locally; any slot can read it.
    • restore_images — before a dependent job runs, copy each parent image’s /workspace into this slot’s workspace, in pipeline (step_index) order: an ordered union, last wins on a shared path (OverlayFS / CI-artifact semantics). Parents are local — no pull. Logs the merge event + order.
    • gc_run_images — prune ephemeral run-scoped images at startup.
  • config: advertise_address + registry_port + runner configure --advertise-address — these drive the dormant cross-host mode (push to a local ephemeral registry + pull from a peer), unused on a single host.
  • loop_runner: execute_job returns JobOutcome; restore before the step, snapshot after success, report output_image (+ image_host only when served) via update_job_status. Re-fit onto #22’s loop (the cancel: Arc<Notify> arg + SlotCounter).

Tests

  • Pure logic (REQ-CI-073/074): run-scoped tag + sanitization, restore_from parsing (same-host null-host kept, no-image dropped, cross-host host kept), advertise-host gating.
  • 111 tests green; cargo clippy --all-targets -D warnings + cargo fmt --check clean.

Not in this PR

  • End-to-end same-host availability (REQ-CI-076) — needs a real multi-slot docker run.
  • v2 fan-in 3-way merge vs nearest-common-ancestor (fail on genuine same-path conflict); v1 is ordered-union + logging.

Pairs with the server contract (restore_from in the claim payload, output_image/image_host persisted) in fangorn/anvil#177.

🤖 Generated with Claude Code

Created Jun 05, 2026 at 19:44 UTC