Summary
On lancedb ≥ 0.32, the background FTS index optimization crashes on every cycle with:
Max offset of N exceeds length of values M
at lance-encoding/.../encodings/logical/list.rs
Because the crash aborts optimize() — which also performs version cleanup — stale index/data files are never reclaimed, so the LanceDB index directory grows unbounded until the disk fills.
Conditions (all three required)
lancedb >= 0.32 (lance-encoding >= 6.0)
- FTS index built with
with_position=True (the previous default)
- an
optimize that merges an unindexed tail — i.e. any writes after the index was first built (reproduces with a tail as small as ~100 rows)
Older lancedb (≤ 0.30.x, lance-encoding 4.x) is not affected.
Root cause
Upstream lance regression in the RepDef unravel_offsets path (lance-encoding v4.0.0 OK → v6.0.0 crash). The offsets restored from the RepDef machinery exceed the values buffer, and arrow's ListArray::try_new rejects them. Reported upstream: lance-format/lance#7653.
EverOS's FTS recall is OR-mode BM25 (MatchQuery) and never uses phrase queries, so the token positions that with_position=True stores are never read — the option was pure overhead that happened to trigger the upstream bug.
Fix
Default with_position=False for FTS indexes. This is lossless (no phrase queries anywhere in recall) and avoids building the position posting List that triggers the crash.
Summary
On lancedb ≥ 0.32, the background FTS index optimization crashes on every cycle with:
Because the crash aborts
optimize()— which also performs version cleanup — stale index/data files are never reclaimed, so the LanceDB index directory grows unbounded until the disk fills.Conditions (all three required)
lancedb >= 0.32(lance-encoding>= 6.0)with_position=True(the previous default)optimizethat merges an unindexed tail — i.e. any writes after the index was first built (reproduces with a tail as small as ~100 rows)Older lancedb (≤ 0.30.x, lance-encoding 4.x) is not affected.
Root cause
Upstream lance regression in the RepDef
unravel_offsetspath (lance-encodingv4.0.0 OK → v6.0.0 crash). The offsets restored from the RepDef machinery exceed the values buffer, and arrow'sListArray::try_newrejects them. Reported upstream:lance-format/lance#7653.EverOS's FTS recall is OR-mode BM25 (
MatchQuery) and never uses phrase queries, so the token positions thatwith_position=Truestores are never read — the option was pure overhead that happened to trigger the upstream bug.Fix
Default
with_position=Falsefor FTS indexes. This is lossless (no phrase queries anywhere in recall) and avoids building the position posting List that triggers the crash.