Skip to content

Todo summary-display projection retirement (2026-10-26)

Boundary Delivered evidence
Goal/source Existing TypeScript migration T3/T4 transaction payoff; baseline c6462f902. One read-only summary-display slice, with no new capability, RPC operation, provider or runtime.
Observable gap Python still selected summary/planning sources, normalized display declarations and assembled handoff displays before asking the typed quota owner to select lanes.
Single owner todos/context_projection.ts now owns standalone summary compaction, source order/deduplication, ready-successor overlays and terminal-inclusive frontier preservation through the existing todo.context.page. todos/read_codec.ts reuses handoffSource; quota planning composes the display in process before lane decisions. Both complete planning decisions remain independent.
Retired symbols/callers Python _compact_todo_summary_item_record, _refs, _TEXT_FIELDS and handoff_context_source are deleted. The bodies of compact_todo_summary_items, todo_summary_source_items and todo_planning_source_items become transport facades. todo_index.py sends raw record facts for both handoff stages. Existing todo_summary.py compact/open callers reach the same raw-fact adapter through attach_todo_handoff_notes; they require no new decision branch. quota_selection.py removes its display-source join and sends raw display facts.
Retained Python placement summary_item.py retains public import signatures, source-key compatibility exports, empty/bounded transport, response validation and todo_text_content_revision. handoff_note.py retains generic JSON conversion with Python string/repr facts for tuples, sets, floats and other non-JSON scalars, batching/private snapshots, rejection propagation and mutable-row attachment identity. Existing handoff-gate source IO/compatibility remains. No Python decision fallback or per-field RPC is added.
Facade deletion condition Delete the summary/handoff transport facades and their raw-fact request carriers after the last Python display, index, quota, management and planning callers consume the existing typed owners in process. Delete todo_text_content_revision only after its last compatibility caller exits. This does not retire the other context-page callers, delegation facts, Turn recovery or monitor-poll facades.
Formats/rollback No persisted format, authority, CAS, writer fence, lease, receipt, provider selection or default changes. Rollback is a code-only revert; no data migration.

Cost and real-path evidence

Production source: summary_item.py 329 → 100 lines, handoff_note.py 150 → 112 lines; Python −273 net, TypeScript +157 net, production −116 net. The seven production files total 242 added / 358 deleted lines. The related refactoring pass reuses the existing handoff/read codecs rather than introducing another owner or RPC leaf. Larger caller retirement is deferred to the existing exits.

One real-CLI trace per command and fixture size (N=1/N=3) gives:

Command Crossings base → candidate Stdout bytes N=1 Stdout bytes N=3
agent-context --phase before_plan 1 → 1 1885 → 1885 2247 → 2247
agent-context --phase after_delegate_result 3 → 3 1612 → 1612 1612 → 1612
Same result phase with a Turn identity 3 → 3 2594 → 2594 2594 → 2594
quota should-run 75 → 74 25520 → 25520 25904 → 25904

The estimated 73-crossing target is not met: the first (empty user) planning call has no display rows and therefore no preceding display RPC to remove. Only the nonempty Agent planning display crossing is retired. Do not remove a second planning decision or absorb an unrelated caller to manufacture the estimate. Fewer crossings do not certify latency improvement; the matched 25-run performance comparison remains external qualification.

The pre-cutover synthetic quota Todo rows and their Python display results are pinned in tests/control_plane_ts/fixtures/todo_summary_display.json. An external isolated-runtime replay with Python/Node wall clocks pinned matches all eight complete CLI outputs byte for byte, including context_id, against the base Python owners. Independent TS cases cover nested-field precedence, legacy identity, Unicode and credential exclusion before truncation, bounded/public-safe blocked causes, open-advancement hint visibility, normalized declarations, last-outcome precedence, ordered source deduplication, explicit false readiness and terminal frontier fields. Python retains real File/SQLite CLI recovery, mutation-identity, large/oversize transport and fail-closed adapter tests, including tuple/set/float facts.

Focused validation: 89 TS tests pass; typecheck, changed-Python ruff, configured mypy (17 files), diff whitespace and the semantic advisory pass. The requested Python set reports 467 passed and one temporary-path depth skip, with four existing legacy-path failures (three quota legacy-provider cases and test_absent_fence_preserves_legacy_path_without_starting_typescript), reproduced with the base Python owners in the same environment. These remain failures, not passing skips. The configured mypy list does not cover the changed Python modules. Real installed-wheel qualification, the minimum Node lane and isolated PostgreSQL CI are unverified here; no PostgreSQL code is changed. This source checkpoint does not certify full CI, installed delivery or a latency gain.

Review correction: summary display now preserves the canonical decision_scope_outcomes[*].schema_version as todo_decision_scope_outcome_v0 by reusing the completion writer’s shared constant, replacing the unregistered decision_scope_outcome_v0; TS regression and File/SQLite quota should-run coverage were added.