100%

Section 06: PlanIndexSchema routing_justification Extension

Status: Complete Goal: Formalize the routing_justification field in the schema so the plan_corpus validator enforces it consistently, and document the intel-graph symbol-plans subcommand usage for detecting stale cross-plan references post-migration.

Success Criteria:

  • scripts/plan_corpus/schemas.py PlanIndexSchema has new field routing_justification: str | None = None (connects to mission criterion: “PlanIndexSchema accepts routing_justification: str | None = None as flat sibling field”)
  • Schema is ADDITIVE — existing plans’ index.md frontmatter (without the new field) still validates
  • .claude/rules/intelligence.md symbol-plans subcommand documentation includes a post-migration-auditing use case
  • plan_corpus check plans/ exits 0 across the entire tree

Context: §04 added the conditional-required validator; §06 formalizes the schema field it validates against. Keeping §06 AFTER §05 (migration) means the schema is extended to capture the state the migration produced, rather than forcing ex-ante speculation about what routing_justification values would emerge. Gemini’s /tp-help response flagged that a nested routing: dict would duplicate what reroute: bool already encodes — this section uses a flat sibling field to avoid that SSOT violation.

Reference implementations:

  • TprInfo dataclass (scripts/plan_corpus/schemas.py:168–172) — precedent for nested-dict validation; deliberately NOT used here because the Gemini-flagged SSOT concern favors flat fields.
  • reroute: bool | None (scripts/plan_corpus/schemas.py:44) — the existing sibling field that routing_justification complements.
  • .claude/rules/intelligence.md §Plan/bug graph queries §symbol-plans — existing subcommand documentation to extend.

Depends on: Section 05 — schema extension captures the migration’s output state; running before migration would require ex-ante field-value speculation.


Intelligence Reconnaissance

Queries run 2026-04-24:

  • scripts/intel-query.sh --human symbols "PlanIndexSchema" --repo ori --limit 5 — confirms the schema dataclass is defined in exactly one location (scripts/plan_corpus/schemas.py) and surfaces its consumers (plan_corpus check, plan-cleanup.py).
  • scripts/intel-query.sh --human callers "PlanIndexSchema" --repo ori --limit 10 — blast radius for the additive field: consumer modules that unpack the schema (plan_corpus.check, plan_validators, plan-cleanup). The additive routing_justification: str | None = None default preserves backward compat for all callers.
  • grep -n "PlanIndexSchema" scripts/plan_corpus/schemas.py — locates dataclass definition at line 40.
  • grep -n "reroute:" scripts/plan_corpus/schemas.py — locates existing reroute: bool | None = None field at line 44.
  • grep -n "symbol-plans" .claude/rules/intelligence.md — locates existing subcommand documentation.

Results summary (≤500 chars) [ori]: PlanIndexSchema at scripts/plan_corpus/schemas.py:40-52 is frozen dataclass with 3 required + 7 optional fields. Adding routing_justification: str | None = None is an additive one-line change. reroute: bool | None at line 44 is the sibling field the new one complements. .claude/rules/intelligence.md already documents symbol-plans <symbol-name> — adding a post-migration-auditing use case is a small prose addition.

See .claude/skills/query-intel/compose-intel-summary.md for the full query protocol.


06.1 Extend PlanIndexSchema with routing_justification field

File(s): scripts/plan_corpus/schemas.py

  • Locate PlanIndexSchema dataclass (currently lines 40–52 per §01 research)

  • Add new optional field:

    @dataclass(frozen=True)
    class PlanIndexSchema:
        """Schema for `plans/*/index.md`."""
        name: str
        full_name: str
        status: str
        reviewed: bool | None = None
        reroute: bool | None = None
        parallel: bool | None = None
        order: int | None = None
        supersedes: list[str] | None = None
        references: list[str] | None = None
        inspired_by: list[str] | None = None
        routing_justification: str | None = None  # NEW — required when reroute: True, forbidden otherwise (enforced by validator from §04)
  • The conditional-required validation logic already landed in §04; this section just adds the schema field so the validator has a typed home for the value

  • Add unit test to existing compiler_repo/tests/plan-audit/ test suite: fixture PlanIndexSchema with reroute: true, routing_justification: "..." parses cleanly; fixture with routing_justification: "..." alone (no reroute:) also parses at schema level (validator in §04 rejects at check time, not schema parse time — keeps schema permissive, validator restrictive)

  • Run schema tests: pytest compiler_repo/tests/plan-audit/ -k PlanIndex exits 0

  • Run full corpus check: python -m scripts.plan_corpus check plans/ exits 0 — no existing plan’s frontmatter breaks on the new optional field

  • Subsection close-out (06.1) — MANDATORY before starting 06.2:

    • Schema extended; tests green
    • plan_corpus check plans/ exits 0
    • Update this subsection’s status to complete
    • Repo hygiene checkcompiler_repo/diagnostics/repo-hygiene.sh --check

06.2 Update .claude/rules/intelligence.md for symbol-plans post-migration auditing

File(s): .claude/rules/intelligence.md

After migration, symbols referenced in plan bodies may have MOVED (e.g., repr-opt section 05’s ReprPlan reference now lives at §21A-llvm.NN.05). symbol-plans subcommand surfaces stale cross-references.

  • Locate §symbol-plans documentation (grep -n "symbol-plans" .claude/rules/intelligence.md)

  • Add a use case entry:

    - **Post-migration cross-reference auditing**: after a plan migration moves content across plan boundaries (e.g., `repr-opt` flattened into `§21A-llvm`), run `scripts/intel-query.sh --human symbol-plans "<symbol>" --repo ori` for load-bearing symbols. Surfaces plans whose prose still references the old location; these references need re-pointing to the new subsection IDs. Use case: after §05 migration of this plan, audit `ReprPlan`, `AimsStateMap`, `IteratorValue`, and other high-traffic symbols.
  • Verify grep: grep -c "symbol-plans" .claude/rules/intelligence.md increments; prose-lint green: python3 scripts/prose-lint.py .claude/rules/intelligence.md exits 0

  • Subsection close-out (06.2) — MANDATORY before starting 06.N:

    • intelligence.md updated with symbol-plans post-migration use case
    • Update this subsection’s status to complete
    • Repo hygiene checkcompiler_repo/diagnostics/repo-hygiene.sh --check

06.N Completion Checklist

  • All implementation subsections (06.1–06.2) are [x] and status complete
  • All section success criteria have corresponding [x] checkboxes
  • grep -c "routing_justification" scripts/plan_corpus/schemas.py returns at least 1
  • python -m scripts.plan_corpus check plans/ exits 0 across the entire tree
  • pytest compiler_repo/tests/plan-audit/ -k PlanIndex exits 0
  • ./test-all.sh green — regression canary
  • Plan sync:
    • This section’s frontmatter statuscomplete, subsection statuses → complete
    • 00-overview.md Quick Reference: Section 06 status → Complete
    • 00-overview.md mission success criteria: check off “PlanIndexSchema accepts routing_justification
    • index.md Section 06 status → Complete
  • Repo hygiene checkcompiler_repo/diagnostics/repo-hygiene.sh --check

Exit Criteria: Schema field landed; plan_corpus check plans/ green; intelligence.md documents post-migration symbol-plans usage; existing plans continue to parse unchanged.