Design spec for the "versioned bundle" cycle binding issues #3 (pack the
per-file embedding store into one contiguous matrix file) and #4 (bind
{corpus snapshot, embed model, index} as one versioned artifact).
Ratified decisions (user-approved across the brainstorm):
- Approach 1: single self-describing file (magic + JSON-header manifest +
row-major f32 payload), loaded with one fs::read. No mmap (a brute-force
full-scan cosine index touches every row per query, so mmap yields no
runtime benefit and is rejected to avoid an unsafe dependency). VectorIndex
and the per-file store are untouched — the store stays the build/resume
path, the packed file is an additive serve-path artifact.
- Mismatch posture: loud but not fatal. A structurally wrong index (corpus
sha256 or embed_model disagreement) builds no VectorIndex and surfaces as a
distinct IndexStatus::Mismatch in diagnostics plus a load-time warning,
instead of silently degrading Mode Hybrid to Lexical. Mode Lexical, which
never needs the index, keeps serving.
- Two iterations, one format: iter 1 delivers the format + `index --pack` +
packed-first load; iter 2 enforces the manifest check and the observable
index_status surface.
grounding-check: PASS (7 load-bearing assumptions ratified by green tests).
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The retrieval-mode enum used opaque single letters `Mode { C, A }`;
neither the identifier nor the operator-facing `--mode a` token
conveyed what the mode does. Rename to self-describing names that map
directly onto the glossary definitions:
Mode::C -> Mode::Lexical (BM25 + tag filter, offline, no IONOS)
Mode::A -> Mode::Hybrid (lexical u semantic -> RRF -> rerank)
Decisions taken (the issue's open questions, resolved):
- CLI canonical tokens are now `lexical` / `hybrid`; the default is
`lexical`. The legacy `c` / `a` tokens stay accepted as
case-insensitive input aliases (zero cost; protects hand-typed
invocations). A unit test pins the alias contract.
- The diagnostics `mode` string (Debug-derived) now emits
"Lexical"/"Hybrid". Verified safe: no downstream consumer parses it.
doctate is the future integrator and embeds the library (the `Mode`
enum), not the JSON string (design spec §103).
- The reserved, out-of-scope generative tier (spec's "Mode B") keeps
conceptual room: a future `Mode::Generative` does not collide with
the retrieval-strategy names Lexical/Hybrid.
Surface: enum + FromStr, CLI defaults and `eval --mode both`
expansion, the private `collect_mode_c`/`collect_mode_a` methods (now
`collect_lexical`/`collect_hybrid`) and their comments, the two
pipeline mode test files (renamed), the eval CLI test, the glossary
(old letter forms demoted to Avoid lists), and the spec CLI synopsis.
closes#2
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The superpowers workflow methodology is no longer in use. Move the
methodology-neutral design spec to docs/specs/ as the project's design
ledger, drop the superpowers-bound implementation plan (it referenced
superpowers sub-skills), and remove the now-dead /docs/superpowers/
.gitignore entry.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>