Skip to content

fix(ci-baton): recover stranded typed-budget planner + stdout-discipline fix - #3

Merged
hyperpolymath merged 3 commits into
mainfrom
fix/recover-stranded-planner
Jun 13, 2026
Merged

hyperpolymath merged 3 commits into
mainfrom
fix/recover-stranded-planner

Conversation

@hyperpolymath

Copy link
Copy Markdown
Owner

Why

PR #2 (feat/ci-check-baton → main) merged at 16:36 as c45590f, but it captured only the CI-baton + sweep work. Two commits were pushed to that branch after it had already merged, so they landed nowhere:

  • 1eb58b7 — route Mesh operational logs to stderr (keep mix bag.sweep stdout pure TSV)
  • 7f0db1e — the entire typed-budget planner increment

This PR recovers both onto main (cherry-picked, re-signed), plus a small follow-up.

What lands

  1. fix(ci-baton) — Mesh operational logs → :stderr. mix bag.sweep's documented contract is "stdout = one TSV line per check"; previously the CI path printed Mesh: … lines to stdout, mixing with the TSV. Now stdout is pure machine output.
  2. feat(ci-baton) — typed-budget planner:
    • Node carries a tropical (min-plus) money cost grade, mirrored across the three layers — Estate.idr (cheapestCapable, the formal objective) → estate.zig (nodes emits name<TAB>cost) → Executor.node_costs/0.
    • Bag.Budget — non-fungible typed budgets (money / mutation / human_review / repair); exhausting one dimension removes a route.
    • Bag.Planner — cheapest capable node the budget can afford; reserve the paid route for work only it can do; gate mutating/irreversible work on a verifier.
    • Bag.ActionResult — structured residue (echo): a relegated pass still owes the GitHub required-status-check; a dirty partial yields a repair obligation.
    • Bag.Mesh.submit_planned wires Planner → execute → residue.
  3. chore(ci-baton) — drop the unused MATCH: TRUE/FALSE debug prints from the Zig match subcommand (the Elixir executor reads only its exit code).

Verification

All three layers green on the recovered tree:

  • Idris — idris2 --build bag.ipkg → 4/4 ✓
  • Zig — zig build test → rc=0 ✓
  • Elixir — mix test → 19 tests + 1 doctest, 0 failures ✓

Cherry-pick applied with zero conflicts; no build artifacts in the diff.

🤖 Generated with Claude Code

hyperpolymath and others added 3 commits June 13, 2026 20:55
… clean)

Integration with the ci-health baton-bridge surfaced that Bag.Mesh.submit_check logged routing/verdict lines to stdout, polluting the machine-readable TSV that mix bag.sweep emits. Operational logs now go to stderr; stdout stays a clean contract.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…tion gate, residue

Adopt the on-point subset of the typed-orchestration design frame (the rest is
split out to hypatia + a budget-planner via dev-notes/prompts). Keeps
bag-of-actions focused on compute routing rather than becoming a generic
orchestrator.

- Node carries a tropical (min-plus) money `cost` grade, mirrored across the
  three layers: Estate.idr (source of truth) + estate.zig + the `nodes` output
  (`name<TAB>cost`), read by Executor.node_costs/0. Idris adds `cheapestCapable`
  as the formal routing objective the Elixir planner mirrors.
- Bag.Budget: typed, NON-FUNGIBLE budgets (money/mutation/human_review/repair) —
  exhausting one dimension is a context change that removes a route.
- Bag.Planner: among capable nodes the budget can afford, pick the cheapest
  (tropical min); reserve the paid route for work whose capability only it has;
  gate mutating/irreversible work on a verifier.
- Bag.ActionResult: structured residue (echo) — a relegated pass still owes the
  GitHub required-status-check; a dirty partial yields a repair obligation.
- Bag.Mesh.submit_planned wires Planner -> execute -> residue end to end.

Tests: Idris builds; 6 Zig; 19 Elixir + 1 doctest — all green. Covers
"paid budget too low -> work needing it suspends, cheap route remains",
"cheapest-capable relegation", "mutation rejected without verifier",
"non-fungible dimensions", and "dirty partial -> repair obligation".

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The Elixir Executor.node_satisfies?/2 reads only the exit code (0 = match,
1 = no match) from the `match` subcommand; the MATCH: TRUE/FALSE text was
never consumed. Remove it so the subcommand is silent and exit-code-driven.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@hyperpolymath
hyperpolymath merged commit ff1c0a0 into main Jun 13, 2026
@hyperpolymath
hyperpolymath deleted the fix/recover-stranded-planner branch June 13, 2026 19:59
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.

1 participant