history
GET /slots/{slot}/entities/{entity_type}/{entity_id}/history
Read an entity's served-score history (trajectory)
The entity's served-score history under the slot, newest first (WP-D5 req 7; items are https://spec.tessera.dev/schemas/entity_state_history.json), with 003 §1 cursor pagination (limit ≤ 200) — one bounded prefix scan per page — and from (inclusive) / to (exclusive) bounds on computed_at (RFC 3339), clamped to the plan's retained window. With threshold (plus label/class for a score series; default the surprise signal) the page carries deviation_started_at: the computed_at of the earliest row of the CURRENT contiguous run of values ≥ threshold, or null when the newest row does not cross. A foreign or unknown slot, or an entity with no history under it, is 404 not_found (003 §3). Requires the read scope; pages meter state_reads (quantity = page size, 002 §11). Where the history store has not been provisioned yet the read is 503 unavailable with details[0].reason == "history_store_unavailable" (retryable).
Operation ID: listSlotEntityHistory · Service: serving-api
Authentication
apiKey(http (bearer)) — Project API key (003 §2):tsk_live_…ortsk_test_…inAuthorization: Bearer. Scoped to exactly one project + environment; scopes are a subset ofingest,read,admin. Keys are stored hashed and shown once at creation.consoleSession(http (bearer)) — Console session (003 §2): Identity Platform JWT. Data-plane calls addX-Tessera-Project+X-Tessera-Environmentheaders, validated against org membership.
Parameters
| Name | In | Required | Type | Description |
|---|---|---|---|---|
entity_id | path | yes | string | The customer's entity id (opaque, 002 §2). |
entity_type | path | yes | string | Customer-declared entity type (002 §2). |
slot | path | yes | string | Deployment slot name (002 §9: the slot is the API-addressable unit and its name is stable while bundles rotate). Resolved within the credential's project only — a slot name that exists in another project is 404 not_found (WP-V2 req 1). |
class | query | no | string | Class of a multiclass label series. |
cursor | query | no | string | Opaque pagination cursor from a previous response's next_cursor. |
from | query | no | string | Inclusive lower bound on computed_at (RFC 3339 UTC). |
label | query | no | string | Score series for threshold (default the surprise signal). |
limit | query | no | integer | Page size (cursor pagination, 003 §1). Maximum 200. |
threshold | query | no | number | Compute deviation_started_at against this threshold. |
to | query | no | string | Exclusive upper bound on computed_at (RFC 3339 UTC). Default now. |
Pagination
Cursor pagination (003 §1): pass limit (max 200) and cursor; the
response is the pagination envelope — data plus next_cursor
(null on the last page).
Responses
| Status | Schema | Description |
|---|---|---|
200 | EntityStateHistoryPage | One newest-first page of history items. |
default | ErrorEnvelope | Error response (003 §1). Every non-2xx response uses this envelope; the HTTP status matches error.code. Rate-limited requests get 429 resource_exhausted with retry_after_seconds and a Retry-After header; the X-RateLimit-* headers ride on EVERY response, success or error (003 §1; plan-driven per API key + endpoint class — WP-B2). A 503 unavailable carries retry_after_seconds too for a lock-wait timeout (SQLSTATE 55P03), a rule preview at capacity (preview_capacity_exhausted), or a label preview during which the erasure of every entity holding its censor clock began (label_preview_clock_entity_erased): how long to wait before retrying. |
GET /slots/{slot}/entities:top
Rank a slot's entities by score, signal or score delta
Ranked reads over the slot's current entity_state rows (WP-D5 reqs 5-6; https://spec.tessera.dev/schemas/ranked_read.json). by=score ranks the current scores[label] (class required for a multiclass head); by=signal ranks signals.behavior_surprise (the v1 signal); by=delta ranks scores[label] minus the entity's history score as of now - window (default 7d, bounded by the plan's retained history). Descending value, ties broken by entity id ascending; rows whose selected field is absent never rank (002 §1); rows written under a model_fingerprint other than the active bundle's are excluded and counted stale_rows_excluded. A cursorless request reuses a ranking snapshot younger than max_age_seconds (default 60, max 3600) or computes one from a bounded scan of the slot (more than 1,000,000 rows is 400 failed_precondition with details[0].reason == "entity_count_exceeded" — the exact-scan v1 contract); the top 1,000 entries persist and the opaque cursor pins one snapshot, so paging never reorders. With threshold, items carry deviation_started_at (the start of the entity's current run at or above the threshold, over the ranked series). A foreign or unknown slot is 404 not_found (003 §3). Requires the read scope; pages meter state_reads (quantity = items returned, 002 §11). Where the history store has not been provisioned yet, by=delta is 503 unavailable with details[0].reason == "history_store_unavailable" (retryable).
Operation ID: listSlotTopEntities · Service: serving-api
Authentication
apiKey(http (bearer)) — Project API key (003 §2):tsk_live_…ortsk_test_…inAuthorization: Bearer. Scoped to exactly one project + environment; scopes are a subset ofingest,read,admin. Keys are stored hashed and shown once at creation.consoleSession(http (bearer)) — Console session (003 §2): Identity Platform JWT. Data-plane calls addX-Tessera-Project+X-Tessera-Environmentheaders, validated against org membership.
Parameters
| Name | In | Required | Type | Description |
|---|---|---|---|---|
slot | path | yes | string | Deployment slot name (002 §9: the slot is the API-addressable unit and its name is stable while bundles rotate). Resolved within the credential's project only — a slot name that exists in another project is 404 not_found (WP-V2 req 1). |
by | query | yes | string | The ranked field. |
class | query | no | string | Class of a multiclass label head (required for multiclass heads). |
cursor | query | no | string | Opaque pagination cursor from a previous response's next_cursor. |
label | query | no | string | Label head name (002 §9 runtime.labels[].name); required for by=score and by=delta, rejected for by=signal. |
limit | query | no | integer | Page size (cursor pagination, 003 §1). Maximum 200. |
max_age_seconds | query | no | integer | Reuse a snapshot computed at most this many seconds ago (default 60, max 3600; 0 always computes). Ignored when cursor is set. |
threshold | query | no | number | When set, items carry deviation_started_at for the ranked series (score series for score/delta, surprise for signal). |
window | query | no | string | by=delta lookback (\<n\>d or \<n\>h, default 7d); must not exceed the plan's retained history (400 invalid_argument). |
Pagination
Cursor pagination (003 §1): pass limit (max 200) and cursor; the
response is the pagination envelope — data plus next_cursor
(null on the last page).
Responses
| Status | Schema | Description |
|---|---|---|
200 | RankedEntitiesPage | One page of the ranking snapshot. |
default | ErrorEnvelope | Error response (003 §1). Every non-2xx response uses this envelope; the HTTP status matches error.code. Rate-limited requests get 429 resource_exhausted with retry_after_seconds and a Retry-After header; the X-RateLimit-* headers ride on EVERY response, success or error (003 §1; plan-driven per API key + endpoint class — WP-B2). A 503 unavailable carries retry_after_seconds too for a lock-wait timeout (SQLSTATE 55P03), a rule preview at capacity (preview_capacity_exhausted), or a label preview during which the erasure of every entity holding its censor clock began (label_preview_clock_entity_erased): how long to wait before retrying. |
GET /slots/{slot}/entities:top-hazard
Rank a slot's entities by the probability of an event within a horizon
Ranked reads over the slot's current entity_state rows by one WP-M17 hazard column: the calibrated probability that target fires within horizon_days (for example "churn within 30 days"). The WP-D5 ranking contract applies unchanged (an additive operation; the closed by enum of listSlotTopEntities is untouched): descending value, ties broken by entity id ascending; rows without the column never rank; rows written under a model_fingerprint other than the active bundle's are excluded and counted stale_rows_excluded; a cursorless request reuses a snapshot younger than max_age_seconds (default 60, max 3600) or computes one from a bounded scan (more than 1,000,000 rows is 400 failed_precondition, details[0].reason == "entity_count_exceeded"); the top 1,000 entries persist and the cursor pins one snapshot. A slot whose active bundle serves no hazard heads is 400 failed_precondition (details[0].reason == "hazard_not_enabled"); a target or horizon_days outside the active hazard config is 400 invalid_argument; a hazard sidecar that fails re-verification is 503 unavailable (details[0].reason == "hazard_sidecar_unverified"). Suppressed entities never rank (WP-V12 req 4). A foreign or unknown slot is 404 not_found (003 §3). Requires the read scope; pages meter state_reads (quantity = items returned, 002 §11).
Operation ID: listSlotTopHazardEntities · Service: serving-api
Authentication
apiKey(http (bearer)) — Project API key (003 §2):tsk_live_…ortsk_test_…inAuthorization: Bearer. Scoped to exactly one project + environment; scopes are a subset ofingest,read,admin. Keys are stored hashed and shown once at creation.consoleSession(http (bearer)) — Console session (003 §2): Identity Platform JWT. Data-plane calls addX-Tessera-Project+X-Tessera-Environmentheaders, validated against org membership.
Parameters
| Name | In | Required | Type | Description |
|---|---|---|---|---|
slot | path | yes | string | Deployment slot name (002 §9: the slot is the API-addressable unit and its name is stable while bundles rotate). Resolved within the credential's project only — a slot name that exists in another project is 404 not_found (WP-V2 req 1). |
cursor | query | no | string | Opaque pagination cursor from a previous response's next_cursor. |
horizon_days | query | yes | integer | One horizon of the active hazard grid, in days. |
limit | query | no | integer | Page size (cursor pagination, 003 §1). Maximum 200. |
max_age_seconds | query | no | integer | Reuse a snapshot computed at most this many seconds ago (default 60, max 3600; 0 always computes). Ignored when cursor is set. |
target | query | yes | string | Target key: a hazard label id, or event: followed by a hazard event type. |
Pagination
Cursor pagination (003 §1): pass limit (max 200) and cursor; the
response is the pagination envelope — data plus next_cursor
(null on the last page).
Responses
| Status | Schema | Description |
|---|---|---|
200 | RankedHazardEntitiesPage | One page of the hazard ranking snapshot. |
default | ErrorEnvelope | Error response (003 §1). Every non-2xx response uses this envelope; the HTTP status matches error.code. Rate-limited requests get 429 resource_exhausted with retry_after_seconds and a Retry-After header; the X-RateLimit-* headers ride on EVERY response, success or error (003 §1; plan-driven per API key + endpoint class — WP-B2). A 503 unavailable carries retry_after_seconds too for a lock-wait timeout (SQLSTATE 55P03), a rule preview at capacity (preview_capacity_exhausted), or a label preview during which the erasure of every entity holding its censor clock began (label_preview_clock_entity_erased): how long to wait before retrying. |
Errors
Every non-2xx response uses the 003 §1 error envelope; error.request_id
matches the X-Request-Id response header, and the HTTP status always
matches error.code:
{
"error": {
"code": "invalid_argument",
"details": [
{
"type": "field_violation"
}
],
"message": "human-readable",
"request_id": "req_01hxample"
}
}
Closed error-code set (003 §1): invalid_argument, unauthenticated, permission_denied, not_found, already_exists, failed_precondition, resource_exhausted, internal, unavailable.
resource_exhausted responses (HTTP 429) additionally carry
retry_after_seconds. See ErrorEnvelope.