# `aborist.evict` Hot ↔ cold tier transitions. The corpus is large (3.47M Wikipedia docs); not every chunk fits in working memory. `evict.py` is the mechanism that moves rarely-touched chunks to a cold tier (still indexed, just stored separately) and rehydrates them on demand from the original source. ## API surface ```python from aborist.evict import evict_to_cold, rehydrate # Move chunks unused for >threshold days to cold tier evict_to_cold(conn, max_age_days=90, max_evictions=10000) # Pull a cold chunk back to hot from its original source rehydrate(conn, document_root="abc123...") ``` ## Invariant: cores never evict `evict_to_cold` filters `WHERE kind='surface'`. Cores are always hot — they're the long-tail-friendly compression layer that justifies evicting their underlying surfaces. Evicting cores would defeat the purpose. ## v9.8 falsification on drift When `rehydrate()` re-fetches a document and the recomputed `document_root` differs from the stored one, the source has changed since ingest (Wikipedia article was edited, HTML page was republished, etc.). The cache record's `falsification_state` flips from `live` to `stale` — every providence record keyed on that `source_root` is no longer admissible to lookups. This is the **drift-detection-as-falsification** discipline: cache hits don't blindly trust historical answers; they trust answers that the SAME source still grounds. ## Tier values `chunks.tier ∈ {'hot', 'cold'}`. Hot chunks live in `chunks.content`; cold chunks live with NULL `content` and a `cold_uri` pointing at the source. The QA pipeline's chunk-fetch path checks `tier`; on 'cold', it triggers `rehydrate` before continuing. ## Source [`aborist/evict.py`](../../aborist/evict.py)