05 / evidence

Falsify first,
then write code

This page describes no features. It answers one question: why believe any of it. Every number below comes from a real measured comparison; every overturned design once looked obviously right.

12 negative results 6 hard constraints 3,335 tests
01

Twelve designs overturned by measurement

This is the ledger of negative results left by the predecessor project, and the reason this one was started. Every row here was once an obviously correct design.

The twelve split into three questions: 4 ask whether a score is enough, 2 ask whether merging can be automatic, 6 ask whether the capability actually runs.

#Original designMeasured readingWhat it became
Scores instead of judgement (4)
01 confidence as a trust gate Model self-report: 192 of 285 pile up at ≥0.9; the whole store has only 8 distinct values Worthless; filtering by score filters nothing
02 vectors for semantic verdicts Five embedding models all fail to separate right from wrong; the distributions overlap Not used for verdicts; recall starts with keywords
03 relevance = entity + skeleton + vector + lexical, weighted Blocks 6/6 unwanted rows, but also 3/4 of the ones you wanted No tuning separated good from bad; dropped
04 cross-corroboration clustered at the token level Of 6 wrong rows, 3 were judged right Corroborate at the entity level instead
Can merging be automatic (2)
05 a deterministic fingerprint to unify across sessions Coverage 8.7% (9/103); loosening it produces false merges No duplicate writes + coarse candidate screen
06 ownership conflicts are urgent, overwrite automatically Entities written by more than one source: 0 rows Record conflicts, never overwrite
Does the capability actually run (6)
07 Chinese FTS split by character 10 real queries should have hit 22 times; actual hits: 0 times, with no error Per-word normalisation + a shadow column
08 distillation progress in the memory transaction Nested transactions made every write fail silently while progress advanced Re-deliverable, idempotent writes
09 space, affect and intent–skill–knowledge as separate dimensions The three spatial tables do not exist in the store; located_at appears 0 times Existed only on paper; cut
10 memory decay / ACT-R activation running Each cycle's window is filled by pins and archives; 0 rows processed Decorative; cut
11 alerts already reach the user The attention table has no human-facing reader; it stops at stored If nobody sees it, it is not delivered
12 the system supports proactive recall MCP has no push channel; the system can only wait to be asked History was never handed over unprompted
Why no vector recall yet

Row 02 is about verdicts; this is about recall. Three reasons, in order of weight.

01 / Good enough

Keywords are already fast and accurate

For a single word, a hit means the index really contains it, not a computed similarity; multiple words are OR-ed, deliberately returning a few extra rows for the model to filter.

1,045 index rows on this machine
0.02–1.1 ms per query
02 / Cost

A small machine cannot carry an embedding model

A resident embedding model takes memory and CPU; we have not measured a hosted embedding service either, and unmeasured pieces do not go on the main path.

Memory and CPU are hard limits on a local node
03 / Complexity

Another index is another set of problems

Another index to sync, invalidate and rebuild; keywords cover the current scenarios. If it is ever needed, it becomes an optional interface with its own table, without touching the core.

Off by default · bolt-on when needed

How it was measured: the local hub's memory.db opened read-only, rc_shadow 1,045 rows, 2026-11-09; SQLite FTS5 MATCH, excluding network and result assembly. Multiple words are OR-ed, not AND-ed: recall runs wide, and the model and the gate narrow it. Also, keyword search works after ingest without an LLM; what is missing is extraction, not lookup.

02

Six non-negotiables

The constraints are the flip side of the negative results. They are not a vision; they are a gate every merge must pass.

C1
Raw text is append-only,
memory can be rebuilt whole
If memory breaks it can be extracted again from scratch while the raw text stays put; each side tracks its own progress. This is the ground that makes mistakes affordable.
C2
Reads never call a model,
judgement happens in the background
Background judgement is quota-limited, re-runnable and retractable; the budget is shared per family.
C3
Every feature ships alongside
the person who uses it, and a test that can go red
A feature nobody uses, with no test that can prove it broke, is not done; that is where the old project died.
C4
Silence is a defect
Writing zero rows counts as an error; the success flag is ignored; there is no data is investigated at top priority; health checks must actually call once.
C5
Signals that skip the model
may only narrow the field
Conclusions belong to the model; ranking and blocking stay apart; the volume a human must confirm does not grow with the data.
C6
The core knows no specific agent
Anything specific to one agent goes into an external converter; tools are set by the hands that actually use them, not piled up over the years.
03

What a test asserts decides what it can catch

The old form asserted only ok == true; the new form asserts how many rows were actually written. The difference is not style: the former is always true when nothing was written.

beforeCan go falsely green
// returned Ok, but wrote no rows
let report = cycle_once(&db)?;
assert!(report.ok);

// transaction not reentrant + reads on a separate pool
// ⇒ every write failed silently, the watermark advanced anyway
// ⇒ this test stayed green for three releases
afterCan go red
// assert the real row delta and watermark
let before = count_rows(&db)?;
cycle_once(&db)?;
let after = count_rows(&db)?;
assert_eq!(after - before, 3);
assert!(watermark(&db)? > before_wm);
The criterion may not use the ok field,
the test asserts row counts.
04

What we claim is part of the evidence

Writing down what has run and what has not keeps the design notes from being read as live data.

Paths that have run

  • debug build and full workspace tests on Windows x86_64
  • converters for four sources pass the ingest check: Claude / MiniMax / Qoder / DSH
  • end-to-end path on synthetic samples and a local loopback
  • aarch64 artifacts started on a real Raspberry Pi (Debian 13 / glibc 2.41)
  • hub self-trial: ingest → extraction → derivation → recall, end to end

What is not stated as fact

  • a week of unattended continuous readings
  • long runs on a real device cut off from the hub (five days offline)
  • the cost curve under multi-tenant sharing
  • recall quality metrics at production scale
  • any claim of being production ready
0modules
contracts, storage, network and entry points each in their own box
0tests
test functions; the criterion checks rows actually written and values within range
0tables
formal memory tables, schema v6
0tools
13 shared memory tools + 28 private tools