Six items from fox's de-novo synthesis (2026-05-01) landing as one atomic commit. Each item references its motivation and respects the v9.8 honesty boundary (no claims of semantic truth, no proof-path contamination by soft signals). NEW DOCS -------- docs/cti-architecture.md Maps today's modules onto the architectural layer cake fox named in his synthesis: PROMETHEUS-Σ (controller) / CTI (claim-lattice reasoning IR) / Merkle-AGI-DAG (commitment) / Reverse-RAG (evidence direction) / v9.8 Providence (admissibility ledger) / Hermes (weak proposer). Per-layer responsibility table + module map showing which existing files implement which layer. The architecture is real; the labels above name what's already there. docs/naming-deferral.md Argues why we keep internal terms (claim_lattice, claim_lattice_pointer, verify_claim_lattice) instead of renaming to architectural labels (CTI, PROMETHEUS-Σ). The rename costs cache invalidation, ~150 test fixture references, schema CHECK migration, blame-history disconnect, mesh peer coordination. The bridge is the cti-architecture mapping doc — read it once, then read code in code's vocabulary and prose in prose's vocabulary. Lists four triggers that would invert the decision. docs/self-reference-distillation-design.md Successor to docs/self-reference-thought-chains-design.md (the flat-source MVP). Maps STRICT claims onto the existing Distiller / Core / derivations infrastructure: each STRICT record becomes a Fact-Core via a new ProvidenceDistiller, with per-cited-chunk Merkle inclusion proofs back to Wikipedia source_roots. The fact-graph grows; new claims attach by inheriting the proof chain. CompositionDistiller (combining facts into new claims) is explicitly deferred — that's reasoning machinery, not infrastructure. docs/test-coverage-audit-2026-05-01.md Maps fox's §11 test list (16 items) against the codebase. 16/16 covered. Documents item #9's manual-quote-rule lifecycle: the rule was retired from pointer mode in commit224bfd6after the bench journey identified it was rejecting factually correct claims; retained in JSON variant where the punctuation-rationale argument doesn't apply. The audit doc itself is the requirements- drift defense. CODE ---- aborist/qa/keys.py:verifier_policy_hash New pure function. Hashes the verifier-relevant subset of policy (answer_mode + claim_lattice_* verifier knobs + entity_policy fields + base_version). Folded into cache_key as an optional 9th dimension via a new keyword arg with backward-compat default None — legacy 8-dim callers continue to work and produce the pre-2026-05-01 hash result. aborist/qa/{runner,query}.py Compute verifier_policy_hash from the policy_variant and pass to cache_key as the 9th dim. Records written from this commit forward bind to the verifier-policy identity. Pre-existing 8-dim records become cache-misses on next lookup — same migration cost as any governance_policy_hash bump. The 9-dim form makes the question "did the verifier rules change?" answerable from cache_key diff alone, separate from "did the prompt change?" CLAUDE.md Adds "old maps vs runtime maps" engineering discipline to the bench-maxing section. Codifies the principle: every base model carries old maps from training time; the runtime carries the fresh map; when they disagree, the runtime wins. Move authority OUT of the model's prior and INTO runtime artifacts (pointer IDs the runtime mints, source spans the runtime interpolates by offset, evidence maps assembled per query, policy hashes that fold prompt/verifier/retrieval into cache_key, hard checks run by the verifier). Hermes' content-addressed-evidence-id hallucination (commitbb8450d) is the canonical case study. TESTS ----- tests/test_keys.py Six new tests for verifier_policy_hash: - only hashes verifier subset (non-verifier fields don't change it) - changes when verifier-relevant field changes - empty-policy → stable - 9-dim cache_key distinct from 8-dim - 9-dim distinct under different verifier hashes - 8-dim form preserved for legacy callers (None == omit) DEFERRED (per fox + naming-deferral.md) --------------------------------------- - PROMETHEUS-Σ as an extracted controller module — the dispatch logic in runner.py + query.py already IS PROMETHEUS-Σ; an explicit prometheus.py is a refactor with no behavior change. Defer until a §5-rename-trigger fires. 507 tests pass (was 501 before, +6 from verifier_policy_hash coverage).
15 KiB
CTI architecture — layer cake mapped onto today's codebase
Date: 2026-05-01 Audience: fox + future blackops shifts. Purpose: name the architectural layers fox's de novo synthesis identifies (PROMETHEUS-Σ / CTI / Merkle-AGI-DAG / Reverse-RAG / v9.8 / Hermes) against the modules that already exist, so future work has a stable vocabulary for which layer it touches.
This is a mapping doc, not a rename. The codebase keeps its internal terms (claim_lattice, claim_lattice_pointer, verify_claim_lattice); the architectural labels (CTI, PROMETHEUS-Σ, Merkle-AGI) live in docs and commit messages where the cross-cutting story matters. See docs/naming-deferral.md for why.
1. The layer cake
┌────────────────────────────────────────────────────────────┐
│ PROMETHEUS-Σ │
│ policy / admissibility / one-shot mode / cache reuse │
└────────────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────────────────────────────────────┐
│ CTI — Clause Tree Intelligence │
│ claim nodes · evidence edges · statuses · falsifiers │
│ (the runtime IR for reasoning, NOT a model output format)│
└────────────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────────────────────────────────────┐
│ Merkle-AGI-DAG │
│ roots · run-DAG · path proofs · audit lineage │
└────────────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────────────────────────────────────┐
│ Reverse-RAG (Merkle Providence) │
│ answer claim → evidence pointer → source span → root │
└────────────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────────────────────────────────────┐
│ v9.8 Merkle Providence Runtime │
│ 8-dim cache_key · falsification states · audit chain │
└────────────────────────────────────────────────────────────┘
│
▼
┌────────────────────────────────────────────────────────────┐
│ Hermes (and any other base model) │
│ weak proposer of natural-language pointer-line clauses │
└────────────────────────────────────────────────────────────┘
The animating principle: the model proposes, the runtime structures, the verifier falsifies, the renderer quotes, the Merkle-DAG commits, PROMETHEUS-Σ admits. Authority moves DOWN the stack — from training-time priors into runtime artifacts.
2. Per-layer responsibility + module map
2.1 PROMETHEUS-Σ (controller)
Owns:
- which
answer_modeis active - whether cache read / write is allowed
- whether a record is admissible for reuse (the 8-dim match + state filter)
- whether a verifier policy changed (governance hash bump)
- whether a run is scoreable under one-shot rules
- which falsification triggers stale a record
Today's codebase:
aborist/qa/runner.py:ask— orchestrates the full lookup → infer → verify → admissibility flow for the per-document pathaborist/qa/query.py:query— same orchestration for the multi-source RAG pathDEFAULT_POLICY(runner) andDEFAULT_QUERY_POLICY(query) — the policy dictaborist.qa.keys.governance_policy_hash— folds policy into the cache_key
Status: Implicit. The layer exists as code but is not named. The de-novo doc proposes naming it; the codebase doesn't need a prometheus.py module today — the dispatch logic in runner.py and query.py IS PROMETHEUS-Σ. (See docs/naming-deferral.md.)
2.2 CTI — Clause Tree Intelligence (reasoning IR)
Owns:
- claim nodes with text + evidence edges
- per-claim statuses (PARSED, NO_EVIDENCE_POINTER, EVIDENCE_LINKED, EVIDENCE_LINKED_PARTIAL, UNKNOWN_EVIDENCE_ID, SOURCE_ROLE_BLOCKED, CITATION_MISMATCH, SCHEMA_INVALID, etc.)
- soft-signal sidecars: lazy-anchor smell, deflection, partial-grounding split, semantic-entailment (designed in
docs/verifier-semantic-gap-design.md) - the boundary between hard checks (lexical, deterministic) and soft checks (heuristic, demote-only)
Today's codebase:
aborist/qa/parse_claims.py:parse_pointer_claims— the model's pointer-line output →ParsedClaimrecords (the CTI compile step)aborist/qa/evidence.py:EvidenceObject— typed evidence nodes withevidence_id(content-addressed) +pointer_id(prompt-facing)aborist/qa/evidence.py:render_claim_lattice— the renderer that interpolates source spans by offsetaborist/qa/verify.py:verify_claim_lattice— the deterministic verifier (six hard checks + sidecar signals)aborist/qa/verify.py:verify_claim_lattice_json— same for the JSON variant
Status: Real. CTI is what claim_lattice already is. The architectural insight from fox's synthesis — that this is an INTERNAL bytecode for reasoning, not a model output format — is the right reading: the model emits weak pointer lines; the runtime parses them into the CTI lattice; the lattice is what the verifier and renderer operate on.
2.3 Merkle-AGI-DAG (commitment)
Owns:
- per-run Merkle DAG over the 9 stages (question / retrieval / evidence_map / prompt / raw_answer / parsed_claim_lattice / verify / render / final_label)
run_dag_root(sha256 of the canonical DAG)run_dag_blob(the structured data for inspection)- the audit-chain integrity (each
audit_event_hashchains to the previous) - inclusion proofs from chunk → document_root → source corpus
Today's codebase:
aborist/qa/dag.py:build_run_dag— emits the 9-stage DAG; returns{root, nodes, blob}aborist/merkle.py— the non-commutative HashCombine + odd-self-duplicate Merkle conventions (Python port ofproxy.unturf.com/pkg/verified/merkle.go)aborist.store.append_audit— the only legal entry point foraudit_events; computesevent_hash = sha256(prev_event_hash || canonical(body))aborist/qa/keys.py:cache_key— the 8-dim composite hash that gates record reuse
Status: Real. The 9-stage DAG was the F-track work earlier in the session.
2.4 Reverse-RAG / Merkle Providence (evidence direction)
Owns:
- the
claim → evidence_id → source_span → source_root → corpusreverse path - per-claim provenance: every claim links forward to an evidence edge that maps to a chunk_root that proves into a document_root that proves into a source_root
- the renderer pulls source text by
(chunk_root, offset_start, offset_end)— the model NEVER owns the quote text; the runtime interpolates it
Today's codebase:
aborist/qa/evidence.py—EvidenceObject(source_root, document_uri, chunk_root, offset_start, offset_end, source_role, text_hash, span, evidence_id, pointer_id). Thepointer_id(E1, E2, …) is what the model sees in the prompt; theevidence_id(content-addressed) is the cache/run-DAG handle. The runtime maps pointer_id → object → content-addressed evidence_id internally.aborist/qa/verify.py:verify_claim_latticestep 6 (citation-overlap check) — theclaim → cited_spanlexical-coverage gateaborist/qa/evidence.py:render_claim_lattice— interpolates source spans by offset, not Hermes text. Synthetic-elision is impossible by construction in pointer mode because the model never produces the quote string.
Status: Real. Pointer mode makes the reverse-RAG direction explicit; the model produces the LEFT side of the chain (claim) and points to the RIGHT side (evidence_id) — the runtime walks the rest.
2.5 v9.8 Merkle Providence Runtime (admissibility ledger)
Owns:
- the 8-dim cache_key:
source_root | question_hash | model_profile_hash | conversation_hash | governance_policy_hash | schema_version | canonicalization_version | chunking_version falsification_state ∈ {live, failed, stale, quarantined}and the rules for transitions- the
providence_cachetable + theaudit_eventschain - the deliberate honesty boundary: NOT semantic truth, NOT hallucination elimination, NOT formal proof — just admissible provenance
Today's codebase:
aborist/qa/keys.py— all eight dimensions hashed intocache_keyaborist/store.py— schema, audit chain, transaction helpersaborist/qa/runner.py+aborist/qa/query.py— the cache-lookup-then-infer-then-write flow
Status: Real and honest. CLAUDE.md "Schema invariants (do not break)" enforces this boundary.
2.6 Hermes (proposer)
Owns:
- emitting weak pointer-line claims like
Steve Jobs co-founded Apple. [E1] - emitting JSON with
evidence_idsreferencing the same pointer ids - nothing else — every other artifact (the lattice, the verdict, the rendered prose, the run DAG) comes from the runtime
Today's codebase:
aborist/qa/client.py:OpenAICompatibleClient— HTTP client with retry on 502/503/504aborist/qa/client.py:StubClient— offline test stubclaim_lattice_system_prompt+claim_lattice_grounding_reminder— the prompt fields that frame Hermes' roleclaim_lattice_json_system_prompt+claim_lattice_json_grounding_reminder— JSON variant
Status: Real. The negation-removal + atomic-claim work earlier in the session was about tightening the proposer's output shape so the runtime has cleaner input to compile.
3. The two information-flow directions
Two flows traverse the layers in opposite directions:
Inference flow (top-to-bottom-then-up):
question → PROMETHEUS-Σ (admissibility check) → cache miss →
retrieval (Reverse-RAG path: titles → chunks → evidence map) →
Hermes prompt (with pointer ids) →
Hermes response (pointer-line clauses) →
CTI compile (parse_pointer_claims) →
CTI verify (verify_claim_lattice) →
CTI render (render_claim_lattice + spotlight excerpts) →
Merkle-AGI commit (build_run_dag + audit_event) →
v9.8 cache write (providence_cache row) →
PROMETHEUS-Σ admit (audit_mode + falsification_state)
Audit flow (bottom-to-top, on demand):
cache_key lookup → record + run_dag_blob →
rebuild CTI lattice from run_dag stages →
re-verify hard checks against current evidence map →
if mismatch: PROMETHEUS-Σ falsifies → state flips
The audit flow is what makes Merkle-AGI O(log N + k) per challenged claim — you don't re-run Hermes; you replay the deterministic CTI verify path against the committed run-DAG.
4. Where each design doc lives
| concern | doc |
|---|---|
| this layer-cake | docs/cti-architecture.md (you are here) |
| QA mode bench journey | docs/qa-modes-bench-2026-04-30.md |
| NLI semantic-gap sidecar | docs/verifier-semantic-gap-design.md |
| Self-reference (flat MVP) | docs/self-reference-thought-chains-design.md |
| Self-reference (deep, distillation-based) | docs/self-reference-distillation-design.md |
| Why we don't rename code to CTI/PROMETHEUS-Σ | docs/naming-deferral.md |
| Bench-maxing discipline | CLAUDE.md "Bench-maxing" section |
| Schema invariants | CLAUDE.md "Schema invariants (do not break)" |
| Convention list | CLAUDE.md "Conventions (do not silently change)" |
5. What this layering DOESN'T claim
Per fox's de-novo synthesis (and CLAUDE.md's existing honesty boundary):
- Merkle-AGI does NOT make full-model verification free. It moves construction to O(N) once; targeted audit becomes O(log N + k). Full-model proof remains expensive.
- CTI is NOT semantic truth. The hard checks are lexical (substring, source-role, evidence-id resolution). Semantic checks (NLI, entailment, predicate compatibility) live in the soft-signal sidecar layer and never enter the proof path.
- v9.8 admissibility is NOT correctness. A STRICT record means "every claim grounded under the current verifier policy" — the policy is fallible (lazy-anchor false-positives, the Great Wall case in the bench journey doc). PROMETHEUS-Σ falsification is the corrective mechanism.
- Reverse-RAG does NOT prove sources are authoritative. It proves the answer pointed at the source the runtime committed to. Source quality is a separate problem (handled at retrieval time via
_classify_source_role, noisy markers, title-purity rerank).
The substrate's honesty boundary stays where v9.8 placed it. The layer cake names the machinery; it does not extend the claims.
6. What's still open
These are the layer-cake-shaped work items still on the roadmap:
- Verifier-policy-hash separation — landing in this commit pass. Fold
answer_mode + parser_version + evidence_schema_version + manual_quote_policy + hard_checks_listinto a 9th dimension that's separate fromgovernance_policy_hash. Prevents cross-mode cache aliasing more cleanly. - Soft-signal taxonomy expansion — the NLI sidecar (
docs/verifier-semantic-gap-design.md) is one. Predicate-compatibility, completeness, counterevidence, source-authority, scope-ambiguity are others. All demote-only, all out of the proof path. Implementations come one at a time as the bench surfaces motivating cases. - Self-reference distillation — STRICT claims become Cores via a new
ProvidenceDistiller(seedocs/self-reference-distillation-design.md). Lets new claims compose from existing facts, not just retrieve them. - PROMETHEUS-Σ explicit naming — deferred, see
docs/naming-deferral.md. The control logic exists; an extractedprometheus.pymodule is a refactor with no behavior change.
The architecture is real. The labels above name what's already there.