List events with their markets (event-first shape).
List events with their child markets and live prices.
Thin delegate to the legacy GET /events handler in
app.main.list_events. The legacy path stays the implementation
surface — this wrapper exists so SDK consumers can discover the
events feed via the v1 OpenAPI schema instead of having to know
about the root-mounted /events route.
Response shape:
{ events: [...], total: int, limit: int, offset: int, cache_source: str, has_sports: bool, message?: str }
On a cold poller cache, the legacy handler returns a 503 with
Retry-After: 5; this wrapper passes that response through
unchanged so SDK retry logic stays uniform.
Authorizations
Issue from /v1/keys (or admin-issued for enterprise tier).
Headers
Your PolySimulator API key
Polymarket-CLOB-compat alias for X-API-Key (underscore form). SDK clients ported from Polymarket can authenticate without changing header names. X-API-Key takes precedence when both are provided.
PM-CLOB-compat dashed-form alias for X-API-Key. Same value semantics as POLY_API_KEY but with HTTP-conventional dash separators. Audit P1 (staging audit 2026-05-16 0817 PR #1296): the per-tier middleware accepts both spellings but the auth dependency originally only matched the underscore form — now both work end-to-end.
PM-CLOB-compat: Authorization: Bearer ps_live_... (or ps_test_...) is accepted as an alias for X-API-Key so py-clob-client and other ported SDKs authenticate without header name changes. Bearer JWTs are NOT accepted here — use the dashboard-auth endpoints for those.
Query Parameters
1 <= x <= 200x >= 0Only show high-volume events.
Cap on child markets returned per event. The poller stores all child markets per event in Redis; this trims the per-event payload at response time for callers that only need the top-N markets.
1 <= x <= 100Filter to a single category slug (e.g. crypto, sports, politics). Case-insensitive substring match against the event's classified category. Categories are populated by the background poller (~5 min cadence) from the event's tags via classify_event. Use unquoted values: ?category=crypto — leading/trailing single or double quotes are stripped defensively for users pasting from Postman.
50Free-text search over event titles + market questions. Case-insensitive substring match with no operator support.
120When false, suppress sports events from the response. Defaults to true for back-compat with the legacy /events endpoint.
Response
Successful Response
Envelope returned by GET /v1/events.
Per-event payloads are typed as Dict[str, Any] deliberately: the
legacy app.main.list_events returns a heterogeneous event dict
whose fields evolve with the poller (markets, enriched prices,
classified category, weather_category, ...). Modelling the envelope
alone is enough to move the OpenAPI output off "schema": {};
SDK consumers consult the docs for per-event fields.
Events on this page (one dict per parent event, with capped child markets).
Total event count matching the filter (across all pages).
Echo of the requested limit.
Echo of the requested offset.
Internal cache tier (e.g. homepage_prebuilt, redisearch_all, empty).
True when sports events were filtered out (include_sports=false path).
Set on 503 (cache warming) and other operational states; absent on success.