refactor(query): learn the hybrid fusion key from a refusal, not a probe

Asking `get_lsm_write_spec` up front to decide how to fuse taxed every hybrid
query, on every table, to learn something almost no table needs -- and that
endpoint is not cheap: it opens the table and does a `checkout_latest()`
manifest reload so a just-set spec is visible.

Ask for `_rowid` optimistically instead and fall back to the primary key when
the server refuses. Only a MemWAL table refuses; the refusal is raised before
the query is planned, so it costs nothing server-side; and it had to be
handled regardless, because a write spec installed elsewhere can arrive
between any two queries. The proactive probe was belt and braces over a
mechanism that already had to exist.

A base table now sends nothing beyond its two legs, covered by a test that
counts request paths. A MemWAL table pays one refused attempt, then remembers
-- `BaseTable::hybrid_pk_fusion_learned` / `note_hybrid_pk_fusion`, seeded by
the refusal and never fetched, so reading it is free.

Deletes the `lsm_enabled` accessor from `BaseTable`, `Table`, the PyO3 and
Python tables, and the type stubs, along with the cache that backed it.

A caller who explicitly asked for `_rowid` still gets the reason rather than a
bare 400: the refusal is translated into the same message the anticipated path
raises. `return_score="all"` turns row ids on for the reranker rather than the
caller, so it falls back like any other query -- an e2e run caught both of
these.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Daniel Rammer
2026-09-23 12:11:28 -05:00
co-authored by Claude Opus 5
parent 959645f1c7
commit 25176778a3
9 changed files with 423 additions and 346 deletions
+11 -7
View File
@@ -1481,13 +1481,17 @@ impl Table {
})
}
/// Whether reads on this table route through the MemWAL. Cached by the
/// remote table, so the hybrid query path can ask on every call.
pub fn lsm_enabled(self_: PyRef<'_, Self>) -> PyResult<Bound<'_, PyAny>> {
let inner = self_.inner_ref()?.clone();
future_into_py(self_.py(), async move {
inner.lsm_enabled().await.infer_error()
})
/// Whether a hybrid query on this table has already been refused `_rowid`.
/// Learned from a previous refusal, never probed, so this is free.
pub fn hybrid_pk_fusion_learned(self_: PyRef<'_, Self>) -> PyResult<bool> {
Ok(self_.inner_ref()?.base_table().hybrid_pk_fusion_learned())
}
/// Remember that this table refused `_rowid`, so later hybrid queries skip
/// straight to the primary-key fusion.
pub fn note_hybrid_pk_fusion(self_: PyRef<'_, Self>) -> PyResult<()> {
self_.inner_ref()?.base_table().note_hybrid_pk_fusion();
Ok(())
}
/// Converge the table's LSM write path into its base table.