Consumer cutover + scraper deletion
Goal
Repoint every consumer of the fragile regex scraper to the JSON loader, then DELETE the scraper and its silent MINIMAL_CATEGORIES fallback. Consumers: reviewer_history.py (_validate_inputs/append/query_observations), verify_tpr_runtime/gates.py (gate_impl_hygiene_categories_loaded, gate_category_in_taxonomy), verify_tpr_runtime/dispatch.py, cross_exam_validation/backfill_history.py. All token-pinning tests stay green.
Implementation Sketch
Replace IMPL_HYGIENE_CATEGORIES = _parse_impl_hygiene_categories(...) with a read from impl_hygiene_rules_runtime.loader (category:subcat token set derived from JSON). Delete _parse_impl_hygiene_categories, _CATEGORY_RE, _SUBCAT_RE, _normalize_subcat, MINIMAL_CATEGORIES (the silent-degradation fallback is removed — a bad JSON load is a hard error, not a 2-token fallback). Update verify_tpr_runtime/gates.py + dispatch.py + backfill_history.py imports. Update tests in tests/test_reviewer_history.py that asserted parser behavior to assert loader behavior; keep the token-spelling assertions (byte-stable contract).
Spec References
scripts/tpr_review_runtime/reviewer_history.py:79-188 (scraper to delete), :300-357 (consumer); scripts/verify_tpr_runtime/gates.py:60-86; :dispatch.py:426-430; cross_exam_validation/backfill_history.py:525.
Work Items
- Repoint reviewer_history.py to the loader; DELETE _parse_impl_hygiene_categories + _CATEGORY_RE + _SUBCAT_RE + _normalize_subcat + MINIMAL_CATEGORIES fallback.
- Repoint verify_tpr_runtime/gates.py + dispatch.py + cross_exam_validation/backfill_history.py to the loader.
- Update tests to assert loader behavior; keep all token-spelling pins green (byte-stable API contract).
Success Criteria
- [sc-f583ac97] Consumers read the JSON loader; regex scraper deleted; reviewer_history + verify_tpr tests green. (probe:
pytest scripts/tpr_review_runtime/tests/test_reviewer_history.py scripts/verify_tpr_runtime/ -q; expect: passed)
Fresh intel (regenerated)
{ “schema_version”: 1, “target”: { “kind”: “plan-section”, “ref”: “impl-hygiene-rules-as-data/s-3d6e6fc4” }, “generated_at”: “2026-06-21T05:23:13.734387+00:00”, “graph_state”: { “head_sha”: “b0bd51a8”, “last_code_import_at”: “2026-06-21T05:19:39.738Z”, “embedding_stale”: false, “insights_stale”: false, “cpg_stale”: false }, “surfaces”: {}, “summary”: “intel-package[plan-section:impl-hygiene-rules-as-data/s-3d6e6fc4] agent-authored dossier”, “degraded”: false, “dossier”: { “objective_symbols”: [], “tiers”: {}, “agent_authored”: true, “difficulty”: { “class”: “routine”, “research_online”: false, “research_mode”: “auto”, “signals”: [], “plan_dir”: “/home/eric/projects/ori_lang/plans/impl-hygiene-rules-as-data” } } }
(full dossier: consumer-cutover—s-3d6e6fc4.intel.json)