Repository navigation
feat(ci): report Baton verdicts to GitHub (commit-status bridge) + nix capability - #7
Merged
Merged
Conversation
Close the last loop named in docs/ci-check-baton.adoc: publish an owned-compute CI verdict to a GitHub PR so a *required* status check is satisfied without a GitHub-hosted runner (zero Actions minutes).
- Bag.GitHubBridge: post a verdict as a commit STATUS via the gh CLI (dependency-free). Status not check-run because a PAT can write statuses (which satisfy a required context) but not check-runs (App-only). Discharges the {:owes, :github_required_check} residue. (6 tests) - mix bag.report: the dispatcher — sweep on owned compute, then report_sweep each verdict to the commit from GITHUB_REPOSITORY/GITHUB_SHA. (context_map_from tested) - nix capability across all three synced layers (Protocol.idr capToTag=13, estate.zig enum/fromString, mesh.ex) + mesh-server-1 tagged; idris2 + zig build green, match mesh-server-1 nix = 0, fail-safe intact. - docs/ci-report-to-github.adoc: trigger recipe + branch-protection cut-over.
Pre-existing + unrelated: 4 suite failures (a zig fmt --check src/estate.zig fixture expects fail but the file is now well-formatted).
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
hyperpolymath
added a commit
that referenced
this pull request
Jun 29, 2026
…rd-close; removes banned nix) (#11) ## bag-of-actions → production readiness: Phases 0–1.5 + partial Phase 2 Lands the prod-readiness work that had accumulated, unpushed, on `feat/prod-readiness-phase0` (rebased onto current `main`, commit series preserved, linear history). Closes the live security holes from the production-readiness audit **and** removes the banned `nix` capability that `main` currently ships. ### What's in it - **Phase 0 — foundations:** `src/crypto.zig` + `src/store.zig` extracted from `main.zig` (pure refactor); `mix release` + fail-closed `Bag.Config` (gated to prod boot — test/dev stay green); de-templated `Justfile` (real `build`/`test`/`release` + `estate-sync` rosters guard); docs reconciled honestly (anti-overclaim). - **Phase 1 — security hard-close (the live exploit):** removed the hardcoded **dev-HMAC-key fallback** → `BAG_ATTEST_KEY` mandatory (≥32B) or refuse (exit 78); **`BAG-CHECK-BATON v2`** envelope binding `mode` + `key_id`; `BAG_MODE` (prod-default, fail-closed); **mandatory ed25519** signing + verification (no HMAC-only / unsigned acceptance). - **Phase 1.5 — bridge greening gate:** `Bag.GitHubBridge` refuses to post a green status unless the verdict is `mode=prod` + `ed25519:verified` — a dev/laptop node can never green a required check (+ 138-line test). - **Phase 2 (partial):** `guix/manifest.scm` + `guix/bootstrap.sh` (reproducible node toolchain), verified on a real `mesh-server-1`. - **Fixes a live estate-policy violation:** removes the banned `nix` capability from `src/estate.zig` / `Protocol.idr` / `Estate.idr` (Guix is canon). `main` currently ships it via the PR #7 bridge merge; this lands the removal. ### Verified green (rebased tree, run not asserted) - `zig build` ✓ (+ `zig-out/lib/zig_fmt.wasm` installed) - `idris2 --typecheck verification/proofs/bag.ipkg` ✓ (4 modules) - `cd bag && mix test` → **1 doctest, 35 tests, 0 failures** - `./scripts/ci-baton-demo.sh` → step-0 fail-closed (no key → exit 78), pass/fail/suspended/pass, tamper rejected two ways (hmac + unsigned) - `just estate-sync` → "all three estate manifests agree" ### Not in this PR (forward roadmap) Phase 2-finish (per-node Guix configs, laptop as 2nd node, pilot branch-protection cut-over), Phase 3 (durable store / claim-lease-commit registry / hash-chained ledger + custody chain / SSH-mailbox transport / dynamic roster / conformance gate), Phase 4 (zero-GHA webhook + observability), Phase 5 (Wasm linear-memory snapshot migration), Phase 6 (estate rollout + OSS scaffolding). Plan: `~/.claude/plans/woolly-zooming-gizmo.md`. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Closes the last loop
docs/ci-check-baton.adocnames ("Publication ... a separate cloud-native bridge"): getting an owned-compute CI verdict back onto a GitHub PR so a required status check is satisfied without a GitHub-hosted runner (zero Actions minutes).Bag.GitHubBridge— posts a verdict as a GitHub commit status viagh(dependency-free). Status, not check-run: a PAT can write statuses (which satisfy a required context) but not check-runs (App-only). DischargesBag.ActionResult's{:owes, :github_required_check}. (6 tests)mix bag.report— the dispatcher: sweep on owned compute →report_sweepeach verdict to the commit fromGITHUB_REPOSITORY/GITHUB_SHA. (context_map_fromtested)nixcapability — across all three synced layers (Protocol.idrcapToTag=13,estate.zigenum/fromString,mesh.ex) +mesh-server-1tagged. idris2 + zig build green;match mesh-server-1 nix→ 0; fail-safe intact.docs/ci-report-to-github.adoc— trigger recipe (thin GHA dispatcher or owned webhook) + branch-protection cut-over. Worked example:hyperpolymath/snifs(itsci-checks.exslives in that repo, not here).Verification
github_bridge_test6 +bag_report_test2).idris2 --build bag.ipkgexit 0;zig buildexit 0;bag_of_actions match mesh-server-1 nixexit 0; bogus cap exit 1.zig fmt --check src/estate.zigfixture expects a fail but the file is now well-formatted — flagged, not touched here).Not in this PR (genuine infra, owner-provisioned)
A reachable
nix-capable node with the toolchain + a repo checkout, the trigger (SSH dispatcher or webhook), and the branch-protection cut-over to thebag / …contexts. Until then,mix bag.reportruns on demand from the CLI.🤖 Generated with Claude Code