one-cortex - Version Notes

Version History

What changed, when, and why. Newest first.

v4.8 Current 2026-08-17

Four instruments were lying at once. Ingest had been dead for thirteen days while reporting success, the eval set was being archived out from under itself, retrieval precision read 0% because one reader looked for the wrong field name, and the only path that actually injects memory into a prompt was retrieving three chunks while every published number was measured at ten.

  • Ingest was scanning empty directories and calling it success. When the engine moved into a shippable package on 2026-08-04, one module kept working out where the store lived from its own file location. It ended up globbing the workspace root instead of the memory directory: 0 daily logs found where there were 188, 5 stale research notes where there were 264. Every two hours it logged "0 ingested, 5 skipped, 0 errors" and nothing noticed for thirteen days. The break is exact in the data - 2026-08-02 fully processed, 08-04 onward untouched. Fixed at the path resolver, then backfilled: 330 daily-log sections and 12 research notes, 0 errors, run as five batches behind a 10-section pilot that measured outcomes first. Store went 961 → 1119 live chunks.
  • The gate that should have caught it did not name it. A standing probe checks every engine module for exactly this fault, and this module was missing from its list. Added, along with the new one below; it flagged the fault on the first run, which is the proof the addition discriminates.
  • Eval sets can no longer be archived out from under themselves. The multi-hop gold set lost 35 of its 100 required chunks in three weeks - not superseded, archived out of existence, files gone from disk. A chunk cited by an eval is now vetoed on both archive predicates and dropped from rollup groups before the merge. Measured on a throwaway copy of the store with archiving forced wide open: guard on, 92 of 92 survive; guard off, 5. Against the retired gold set it covers 31 of 31 historical losses.
  • Retrieval precision was never 0%. Every writer of the feedback log stamps ts; the health reader alone looked for timestamp, so date parsing raised on every entry, the window came back empty, and precision computed to zero in three consecutive audits. The stream was never empty. It now reads a real number, which is low enough to raise its own alert - that is the point.
  • The recall path was retrieving three chunks, not ten. Every published retrieval number was measured at ten. The hook that actually injects memory into a prompt was hardcoded to three, worse than either figure under discussion. Swept the whole range on the 46-question gold: full-set hit 0.196 at k=3, 0.283 at k=10, monotonic with no plateau, for 17% more injected text. Raised to ten.
  • Sixty-three session records came back. A supersession pass had marked session-end records as overridden by later, unrelated sessions - one topic's record invalidated by a different topic's. They were excluded from retrieval while still being counted as targets by the eval, which is why the retrieval scores had been quietly depressed for weeks. Restored, with the rule that produced them now blocked at the source.
  • The published brain was one third dead. The visualization exported every chunk file on disk - 4,512 of them, of which 3,402 had no router entry at all: memory that had already been archived or merged away. It now exports what the router actually holds (1,110 chunks, 21,495 edges, zero edges pointing at nothing).
v4.7 2026-07-14

Recall stops losing answers it already holds. When a fact is buried deep in the store, a keyword grab now drags it into the candidate pool so it can actually surface.

  • The real failure was upstream. Some recall misses weren't a ranking problem - the answer chunk never entered the candidate pool at all. For a terse jargon query, the one chunk holding the answer sat at embedding rank ~399, far outside the 20-chunk rerank pool, so no reranker or overlap rescue downstream could ever touch it. Proven with two cross-encoders (BGE + a domain fine-tuned MiniLM) rescuing 0/3 - the pool, not the gate, was the wall.
  • Lexical rare-term injection. On top of the meaning-based search, recall now also does a keyword grab: distinctive rare phrases in the query pull every chunk whose full text contains that phrase into the pool, regardless of how far it ranked by cosine. The buried answer finally enters the pile before anything decides.
  • Admit path chosen by eval, not assumption. Two gates were wired and measured - a distinctive-overlap gate vs a cross-encoder rerank over the widened pool. The rerank gate won: rejected-answerable questions went 12/15 → 15/15 with zero extra garbage admitted (held flat at 5/15), stable across the threshold band. The overlap-only gate fixed the same 15 but leaked one extra false positive, so it was dropped.
  • No regression, fully reversible. Multi-hop gold hit@10 held at 0.333. Bigram matching only (unigram content matching leaked 13/15 garbage and shipped off). Config-gated behind a single flag; every injection is logged.
v4.6 2026-07-05

Auto-recall stops fighting the maintenance daemon, a resident retriever keeps the index warm, and hook-injected prompts no longer trigger recall.

  • Read path no longer blocks. Every retrieve was firing three lock-held full-file rewrites (synapses, schemas, and the 1.4MB router), which serialized against the 2-hour maintenance daemon and pushed recall past a 25s cliff - silently killing auto-recall for 11 days. Reads now append a single unlocked line to a read journal; the maintenance loop folds it back into the router. Retrieve dropped from >25s to ~1.1s, with access counts verified folding through intact.
  • Resident warm retriever. A long-lived process holds the embeddings, TurboVec index, and router in RAM and serves fact + procedural recall over a unix socket (launchd-kept, with a cold-path fallback if the socket is down). Warm queries return in ~0.5s.
  • Hook gating. The recall hook now skips internally-injected prompts (session boot, system reminders) via a marker denylist, so recall only fires on genuine user turns.
v4.5 2026-06-10

The knowledge graph goes live in retrieval, the maintenance loop runs itself, and the ranking layer is proven on an external benchmark.

  • Graph fusion enabled. Entity-graph results now fuse into live retrieval via weighted RRF with the vector head pinned (top-3). Multi-hop full-set hit@k 0.477 → 0.500 and set-recall 0.682 → 0.693, with zero regression on single-hop (R@1 0.993).
  • Self-maintaining graph. Nightly 05:15 refresh chain: incremental entity re-extraction → graph harvest → community summaries → procedural auto-distill. Kickstart run re-extracted all 758 chunks into a clean 482-entity graph.
  • Cluster summary tier. Louvain communities over the entity graph with LLM-written summaries - broad "what do I know about X" questions route here instead of chunk retrieval.
  • Reranker verdict: keep disabled. A domain fine-tuned cross-encoder (925 training pairs, hard negatives) scored R@1 0.701 vs the existing multi-signal blend's 0.989. The blend stays; the experiment is documented.
  • LongMemEval benchmark. 500-question external benchmark (LongMemEval-S cleaned): R@10 0.882; the engine's blended scoring lifts NDCG@10 0.522 → 0.738 (+41%) over vector-only, with the biggest gains on multi-session and temporal-reasoning questions. Run fully sandboxed; the live store untouched.
  • Supersession scan clean. Full-store contradiction scan: 0 proposals over 756 chunks after the graph rebuild.
v4.4 2026-06-08

Multi-workspace foundations and a pluggable, compressed index backend.

  • Scope routing. Memory can now be isolated per workspace (private / shared / global) with origin-stamped chunks. Off by default - today's behavior is byte-identical - and eval-gated so isolation is proven before it's ever enabled.
  • Pluggable index backends. Retrieval now runs on one of three backends: pure Python, NumPy (vectorized, exact), or TurboVec.
  • TurboVec live. A 4-bit quantized index, ~26× smaller than the raw vectors (8.70MB → 0.33MB) at recall@5/@10 of 0.975. Auto-rebuilds as memory grows and degrades safely to NumPy then Python if anything is missing.
  • Backfill. All 764 existing chunks stamped with scope and provenance; router backed up first.
v4.3 2026-05-12

Mesh repair and retrieval hygiene.

  • Associative-mesh repair pass and synapse hygiene fixes.
  • Retrieval scoring and grading refinements building on the v4.1 line.
v4.1 - v4.1.1 2026-05

Forensic fixes to the feedback and daemon paths.

  • Repaired the missed-retrieval signal that had been silently zero for hundreds of daemon cycles.
  • Reworked grading into an 11-axis vector so stability is one input, not the whole grade.
  • Daemon ingest cap and wallclock guards to keep maintenance cycles bounded.
v4.0 2026-05-17

Nineteen improvements across all twelve layers, generated via 3-agent review and weighted vote.

  • Atomic WAL writes, dopamine-gated promotion, spreading-activation tiebreakers, cosine reconsolidation.
  • Prediction-error replay, adaptive reward weights, schema hierarchy, hybrid episodic search.
  • Topic-aware hot tier, consolidation dedup routing, observer reconciliation, and an adversarial self-test.
v1.0 - v3.x 2026-03 → 2026-05

From a flat-file replacement to a twelve-layer neural architecture.

  • v1.0 - the foundation: chunking, a router index, local embedding search, fact/narrative split, a feedback loop, rollups, and a maintenance daemon.
  • v2 - six neural layers added on top: variable decay, association, and the first consolidation behaviors.
  • v3.x - extended to twelve layers: episodic memory, persistent working memory, consolidation triggers, reward-driven learning, the glial observer network, and decoupled reward normalization, plus scoring-precision fixes.