scene_service.persistence¶
Object persistence — survives scene restarts so the registry warm-starts instead of re-accumulating every stable object through the min_observations filter from scratch.
Backed by an embedded milvus-lite DB owned solely by the scene process (one .db file, single writer — no sharing with system/memory’s memsearch DB). Writes happen at the low-frequency scene-graph builder cadence; reads happen once at boot. Each row carries a caption embedding so a future G3 object-search layer can reuse the same table; when no embedder is wired (e.g. the VLM-fallback perception path that has no CLIP), a fixed placeholder vector is stored so the collection stays well-formed.
Rows are partitioned by map_id: an object’s pose is only meaningful in the map frame of the SLAM map it was observed on, so warm-restore loads exactly the current map’s objects and never mixes two maps. The primary key is the composite “{map_id}::{object_id}” so the same object_id may exist on different maps without colliding on upsert. Until mapping emits a real map identity, map_id is a deploy-controlled string (SCENE_MAP_ID, default “default”) — this stays internal to scene and touches no atlas/MCP contract.
Classes
|
milvus-lite-backed store for SceneObject current-state. |
- class scene_service.persistence.ObjectStore(db_path: str, *, map_id: str = 'default', dim: int = 512)[source]¶
Bases:
objectmilvus-lite-backed store for SceneObject current-state.
Upsert is keyed by the composite “{map_id}::{object_id}” primary key, so a row holds the latest state of an object on a given map (no version history in v1 — version mirrors observation_count). All methods are synchronous; callers run them off the asyncio loop or inside an already-held registry lock as appropriate.
- close() None[source]¶
Close the client and release the milvus-lite server so the next boot can re-open the same .db file (mirrors memsearch’s cleanup).
- delete_map(map_id: str) int[source]¶
Delete persisted scene objects belonging to one map partition.
The collection is shared, so the filter is mandatory: deleting a map must never affect objects captured for another spatial map.
- load_all(*, limit: int = 16384) list[SceneObject][source]¶
Return this map’s persisted objects as SceneObject`s for warm restore (rows of other maps are filtered out by `map_id).
Restored objects come back missing=True (known but not currently observed) with their persisted last_seen; re-observation flips them back via data association. The embedding column is intentionally not read back — restore needs only scalar state. A query error is logged at error level and yields an empty list rather than failing boot — this is distinct from a genuinely empty DB, which returns [] silently.
- property map_id: str¶
The sanitized map id this store is scoped to.
- persist(pairs: list[tuple[SceneObject, str | None]]) int[source]¶
Upsert (SceneObject, caption) pairs under this store’s map_id (composite pk “{map_id}::{object_id}”). Caption falls back to the class name when None. Returns the number of rows written; a milvus error is swallowed (logged) so a bad write never kills the builder tick.