The phrase-pattern retrieval route (commit 1b8677d) closed the
RETRIEVAL side of reference-frame failure; this ticket closes
the ANSWER side.
New module aborist/qa/frame.py:
FrameDetection dataclass (frame_kind, reference_title,
reference_uri, confidence). Sidecar — never enters cache_key
or governance_policy_hash.
detect_frame(question, sources, phrase_match_roots) — heuristic
detector. Reference-frame classification fires when:
(a) phrase route surfaced at least one source, AND
(b) at least one phrase-matched source is a reference work,
determined by:
- title parenthetical disambig (`(novel)` / `(film)` /
`(play)` / `(franchise)` / etc.), OR
- body sample contains ≥3 DISTINCT fiction markers
(novel / published / protagonist / plot / ...).
Distinct-marker count keeps the heuristic robust against a
history article saying "novel approach" twice.
aborist/qa/query.py:
Calls detect_frame for lattice modes only. Body sample uses the
ARTICLE LEAD (chunk_idx=0, post-wikitext-strip) — fiction
markers cluster in the lead on Wikipedia, not in plot chunks
that may have been query-relevance-ranked higher.
New policy field claim_lattice_polarity_preamble injected as a
user-role message before the grounding_reminder when
frame_kind == "reference". Format-string with
{reference_title} placeholder.
Result dict carries frame_detection (kind / title / uri /
confidence) for renderer + bench consumption.
aborist/cli.py:
Renderer adds a `reference frame: <title>` line when
frame_detection.kind == "reference". Skipped for literal /
no-phrase-route / ambiguous rows.
Live verification — Orwell case:
PRE : "The text does not directly state that Oceania has always
been at war with East Asia."
POST : "In George Orwell's dystopian novel Nineteen Eighty-Four,
the nation of Oceania is always at war with Eastasia,
but this is a result of propaganda and doublethink, not
actual historical continuity. The war with Eastasia is
a fabricated conflict to maintain control..."
Multi-frame compilation: distinguishes propaganda claim from
fictional-actual continuity, exactly the polarity contract from
the ticket §2 abstraction.
Literal queries (capital of france) unchanged — polarity preamble
only injects when frame_kind classifies as "reference".
22 new tests (19 in test_frame.py + 3 in test_cli_render.py).
Full suite: 734 passed (was 712, +22).
Directive D3 status: ½ → ✓. Ticket #000002 closed.
All seven structural directives now ✓:
D1, D2, D5 (were ✓);
D3 #000002, D4 #000001, D6 #000003, D7 #000005 (closed in this
series).
3 KiB
3 KiB
Aborist tickets — index
Aborist uses a flat ticket-NNNNNN-<slug>.md convention for actionable
proposals: defects with a known root cause, design proposals awaiting
go/no-go, or scoped enhancements queued for future implementation.
Convention
- Filename:
docs/ticket-NNNNNN-<slug>.md. The ID is a six-digit zero-padded integer; the slug is hyphen-lowercase and short enough to stay readable on a 100-column terminal. - Numbering: monotonic, never reused. Pick the next free integer
greater than every existing ticket. The current next ID is on the
Next IDline below; bump it when you open a ticket and commit the bump in the same commit as the new ticket file. - Header: every ticket starts with
# Ticket #NNNNNN — <short title> **Status:** open · awaiting go/no-go (or "in progress", "closed") **Opened:** YYYY-MM-DD **Scope:** <one-liner — what this ticket is for> **Audience:** <who reads this> **Hard constraint:** <invariants this ticket commits to NOT break> - Body: problem statement, design choices with trade-offs,
recommendation, implementation sketch, scope boundaries, status.
See
ticket-000001-retrieval-keywords-audit-gap.mdfor a worked template. - Closure: when a ticket lands, flip Status to
closed · landed in commit <sha>and leave the file in place. Do not delete tickets; they are the design log.
Distinction from other docs
docs/ also contains architecture references and bench journey notes
that are NOT tickets — they describe state of the world rather than
proposing change. Examples that stay un-numbered:
cti-architecture.md(architecture reference)mesh.md,mesh-deploy.md(architecture + ops reference)naming-deferral.md(naming convention reference)qa-modes-bench-2026-04-30.md(point-in-time bench journal)verifier-semantic-gap-design.md,self-reference-thought-chains-design.md(older design docs that pre-date the ticket convention; leave as-is unless retroactively promoting one to a ticket adds value)
If a doc proposes change AND awaits a decision AND has scoped implementation cost, it's a ticket. Otherwise it's reference.
Index
Newest first. Update on every open/close.
| ID | Title | Status | Opened | Directive |
|---|---|---|---|---|
| #000005 | Label ladder migration (POINTER-LINKED → …) | closed · 2026-05-02 | 2026-05-01 | D7 |
| #000004 | Directive coverage in bench summary | closed · acd1f9c |
2026-05-01 | D8 |
| #000003 | Anchor-class warrant generalization (Module H+) | closed · 2026-05-02 | 2026-05-01 | D6 |
| #000002 | Reference-Frame Polarity Contract (Module L) | closed · 2026-05-02 | 2026-05-01 | D3 |
| #000001 | Retrieval-keywords audit gap | closed · 2026-05-02 | 2026-05-01 | D4 |
Next ID
000006