Skip to main content

State reads

The low-latency read surface — five endpoints, all served from the state and ledger stores (never a database query per request):

EndpointReturns
GET /slots/{slot}/entities/{type}/{id}/stateone entity's embedding + scores + freshness
POST /slots/{slot}/scores:batchup to 1,000 entities in one call
GET /entities/{type}/{id}/eventsthe entity's event timeline (newest first, cursor-paginated)
GET /entities?type=…&id_prefix=…entity lookup with first/last-seen and event counts
GET /entities/presence?type=…&id_prefix=…entity lookup over recorded history and current scores

The quickstart's final step is a worked state read with output.

The freshness contract​

Every scored response carries a freshness object — all four fields, always:

{
"freshness": {
"event_cursor": { "timestamp": "2025-04-25T13:46:00Z", "event_id": "ord-000009" },
"computed_at": "2026-07-08T21:46:58Z",
"bundle_id": "bnd_01kx1v5gd74hxnrg7pfxv7jdcx",
"model_fingerprint": "5320b447…"
}
}

In Phase 1 states are batch-refreshed, so freshness is what makes staleness visible and honest: event_cursor is the last event this state incorporates; computed_at is when it was written; bundle_id and model_fingerprint identify exactly which model produced it. Alert on event_cursor age, not on hope.

Batch reads​

scores:batch takes up to 1,000 entity ids and answers from one batched storage read. Per-entity misses come back as typed not_found entries in position — a missing entity never fails the batch. Use include to select embedding, scores, or both; embedding_encoding=base64 returns the raw float32 bytes when JSON float arrays are too heavy.

Timelines and lookup​

Timelines serve the raw canonical events (plus received_at and source_id envelope fields only) — useful for debugging "why does this user score this way" by looking at exactly what the model saw. Lookup (GET /entities) finds ids by exact match or prefix with first/last-seen timestamps and event counts.

Entities ingested in batch can have current scores without a recorded lifetime summary. GET /entities/presence takes the same type plus id or id_prefix and returns every entity that has a lifetime summary, current scores in a deployment slot, or both: each item carries the optional summary and the served_slots that hold its scores, in the same id order. Without a summary, first/last-seen and event counts are unknown, not zero. An empty data page means the id has neither.

All reads are metered as state_reads and rate-limited per key (X-RateLimit-* headers on every response).