core/docs/analysis/r3-1-router-integration-2026-06-08.md
Shay 73345e641e feat(contemplation): wire R3 into the multi-organ router + pass manager (R3.1)
classify_r3 normalizes the rate reader into a ComprehensionAttempt; route_setup now tries R1/R2/R3 (same exactly-one-setup_correct rule); the pass manager solves+verifies a routed r3_rate setup (solve_rate + reused answer-choice verifier); unsupported_temporal_state dropped from the unsupported-family set so temporal_state -> REFUSED_KNOWN_BOUNDARY. Organ gains r3_rate.

Terminal matrix (verified): 6 solved->SOLVED_VERIFIED; rate_unit_mismatch+combined_rates->PROPOSAL_EMITTED(unsupported_rate_duration); non_integer/missing_time/temporal->REFUSED_KNOWN_BOUNDARY; exactly 2 proposals (the rate-like gaps only).

REGRESSION CAUGHT+FIXED: R3's reader returned missing_rate (a substantive boundary) on non-rate R2 text, blocking r2-011's legitimate missing_total_count proposal via boundary-first. Fix: missing_rate only when a duration is present; else not_rate_shaped -> input_shape (not-my-domain) — same discipline as the N6 category_pair_not_found fix. r2-011 proposes again; R1/R2 unaffected. R1 7/0/3, 15-case 15/0/0, R2 10/0/0, R3 8/0/0 unchanged; off-serving; 121-test smoke green incl. invariants + idle contract suites.
2026-06-08 02:05:34 -07:00

54 lines
3.1 KiB
Markdown

# R3.1 — R3 wired into the contemplation router (ledger)
**As of:** R3.1, on `main @ a320c69a` + `feat/r3-1-router`.
R3.1 completes the growth loop for the single-rate organ: R3 is now a first-class organ in the
multi-organ router and contemplation pass, so a rate problem the reader can't yet handle is
classified and (for genuine rate gaps) emits a proposal-only artifact — surfaced by the existing
read-only `idle_tick` review. The chain is now whole:
```text
R1 / R2 / R3 organs → route_setup → contemplation pass → proposal-only artifacts → proposal review → idle_tick visibility
```
## What changed
- `core/comprehension_attempt/model.py``Organ` gains `r3_rate`.
- `core/comprehension_attempt/classify.py``classify_r3` normalizes the rate reader's output
into a `ComprehensionAttempt` (deterministic rate signature).
- `core/comprehension_attempt/router.py``route_setup` now tries R1, R2, **and R3**, with the
same exactly-one-`setup_correct` rule (zero → refuse, ≥2 → ambiguous).
- `generate/contemplation/pass_manager.py` — a routed `r3_rate` setup is solved + verified
(`solve_rate` + the reused answer-choice verifier); `unsupported_temporal_state` is dropped from
the unsupported-family set so `temporal_state` is a generic `REFUSED_KNOWN_BOUNDARY`.
## Terminal matrix (verified)
| R3 case | Terminal | Proposal? |
|---|---|---|
| supported single-rate (6 solved) | `SOLVED_VERIFIED` | — |
| `rate_unit_mismatch` (minutes vs /hour) | `PROPOSAL_EMITTED` (`unsupported_rate_duration`) | ✅ |
| `combined_rates` | `PROPOSAL_EMITTED` (`unsupported_rate_duration`) | ✅ |
| `non_integer_solution` (inverse) | `REFUSED_KNOWN_BOUNDARY` | — |
| `missing_time` (underdetermined) | `REFUSED_KNOWN_BOUNDARY` | — |
| `temporal_state` (clock time) | `REFUSED_KNOWN_BOUNDARY` | — |
Exactly **2** proposals over the rate gold — only the rate-like unsupported features
(`rate_unit_mismatch`, `combined_rates`), never the boundaries.
## Anti-over-broad-refusal fix (a regression caught in R3.1)
Adding R3 to the router initially **blocked an R2 proposal**: R3's reader returned `missing_rate`
(a substantive boundary) on R2's `r2-011` (a non-rate problem), and boundary-first classification
let that block R2's legitimate `missing_total_count` proposal. Fix: R3 claims `missing_rate` ONLY
when rate-like structure (a duration) is present; otherwise it refuses `not_rate_shaped`
`input_shape` (not-my-domain). So **R3 never claims a substantive boundary on R1/R2 text** — the
same discipline as the N6 `category_pair_not_found` fix. `r2-011` proposes again; R1/R2 unaffected.
## Invariants held
R1 **7/0/3** · 15-case **15/0/0** · R2 reader **10/0/0** · R3 reader **8/0/0** (answers 6/0/6) ·
serving unchanged · off-serving · 121-test smoke green incl. architectural invariants and both
existing idle contract suites. No `AMBIGUOUS_ORGAN` on any gold (the three organs are exclusive).
## Next
Per the agreed sequencing: **R3.2 — explicit unit conversion** (minutes↔hours, exact rational
only, no floats), which directly closes the `rate_unit_mismatch` gap this loop now surfaces as a
proposal. Combined rates / multi-agent composition come after.