feat(aura-runner): TapPlan + layered fold registry; run_signal_r re-wired onto the shared pair

The #283 registry model's assembly seam: tap_plan.rs carries
TapSubscription (Named{label, params} — fully data-expressible — |
Live(closure), the single non-data variant), TapPlan (name →
subscription + default; the plan travels with the FoldRegistry it
resolves against, the Env-at-resolve pattern, so layered hosts inject
vocabulary as data), and the registry itself: eight core entries
(record, count, sum, mean, min, max, first, last), each with a doc
line (help + roster-enumerating refusals) and a scalar-typed param
schema (all v1 entries param-less; the seam ships now because it sits
in every entry's build signature). Typed TapPlanError refusals fire
pre-bootstrap, before any store I/O; the terminal Store variant keeps
the established "writing tap traces failed" register bytes.

bind_tap_plan/BoundTaps is the shared wiring pair both declared-tap
entry points call; run_signal_r is re-wired onto it here (Recorder
bind + post-run try_iter drain replaced — no O(cycles) retention, no
per-cycle heap), with all six callers threaded (both CLI run-arm and
the four example-identity test calls pass TapPlan::record_all()).
run_measurement follows in the next commit.

Registry growth stays a new Rust entry (C25); a layer-registered
entry is pinned by the injection test, param validation by a
schema-carrying test entry (missing/mismatched/unknown all refused
with named messages).

Verification: cargo build --workspace clean; aura-runner 85+ tests
green incl. both example-identity anchors; tap_recording byte-compat
anchors green (recorded traces byte-identical, tap-free writes
nothing, duplicate-tap refusal unchanged); clippy -D warnings clean.

refs #283 refs #77
This commit is contained in:
2026-07-21 23:18:54 +02:00
parent 92e281e4ec
commit d8ef9de5c2
4 changed files with 671 additions and 43 deletions
+3 -1
View File
@@ -45,6 +45,7 @@ use aura_measurement::information_coefficient;
// (a sibling module reaching it via `crate::blueprint_axis_probe_reopened`,
// the crate-root re-export this `use` gives it), not from this module itself.
use aura_runner::member::{blueprint_axis_probe, blueprint_axis_probe_reopened, run_signal_r, wrapped_bound_names, RunData};
use aura_runner::TapPlan;
#[cfg(test)]
use aura_runner::member::{run_blueprint_member, wrap_r, SYNTHETIC_PIP_SIZE};
// The family builders (blueprint sweep / walk-forward / MC), the shared
@@ -1765,7 +1766,7 @@ fn dispatch_run(a: RunCmd, env: &aura_runner::project::Env) {
None => Vec::new(),
};
let data = run_data_from(a.real.as_deref(), a.from, a.to);
let report = run_signal_r(signal, &params, data, a.seed.unwrap_or(0), env);
let report = run_signal_r(signal, &params, data, a.seed.unwrap_or(0), env, TapPlan::record_all());
println!("{}", report.to_json());
} else if has_tap {
// Measurement path: wrap_r-free closed guard via the signal's own
@@ -3099,6 +3100,7 @@ mod tests {
RunData::Synthetic,
0,
&env,
TapPlan::record_all(),
);
let member4 = &family.points[0].report; // slow=4 is the first odometer point
assert_eq!(member4.metrics, single.metrics, "loaded sweep member == single run");