Concepts
Events and the feed, and how channels differ from preferences.
Events & the feed
Everything starts with an event — a named thing that happened, with an
event_code like training.completed or billing.balance_low. The
platform maintains a fixed catalog of events; you can read it with
GET /v1/notifications/preferences/catalog.
Among what it covers:
| Category | Example events | Emitted when… |
|---|---|---|
| Data | ingestion.completed, ingestion.failed, ingestion.schema_drift | an import finishes, fails, or a source's schema changes |
| Modeling | training.completed, training.failed, pipeline.promotion_ready | trainings finish and pipelines propose promotions |
| Deployments | deployment.promoted, deployment.failed, inference.error_rate_high | deployments change state or serving health degrades |
| Goal Alerts | alerts.goal_alert_triggered, alerts.goal_alert_critical | one of your goal alert rules matches a forecast |
| Billing | billing.balance_low, billing.payment_failed, billing.plan_renewed | credits run low or a payment succeeds / fails |
| Security | security.new_device_login, security.api_key_created | a new device signs in or an API token is created |
Every event carries a category (for grouping), a severity (info,
success, warning, or critical), a rendered title and body, and a
link back to the relevant page.
When an event fires for you, one row lands in your feed — the
per-account inbox behind the in-app bell. Feed items are yours alone:
notifications address users, not workspaces, which is why nothing in
this section takes an X-Workspace-Id header. Events are deduplicated, so
a retried operation never produces duplicate feed rows. info and
success items expire after 90 days; warning and critical items stay
until you deal with them.
Channels vs preferences
Two separate dials control delivery — it's worth keeping them straight:
| Answers | Managed via | |
|---|---|---|
| Preferences | Does this event fire for me, and on which channels? | /v1/notifications/preferences |
| Channels | Where do those deliveries physically go? | /v1/notifications/channels |
The channels themselves come in two groups:
- Built-in —
in_app(the feed),email, andwebsocket(Realtime). These work with no setup. - Configured endpoints —
slack,teams,pagerduty, andwebhook. You create one or more endpoints per type; deliveries fan out to every enabled endpoint of the matching type.
Preferences and endpoints are deliberately decoupled: you can enable the
slack channel for an event before configuring a Slack endpoint — it's a
harmless no-op until an endpoint exists.
Transactional events can't be silenced. Payment receipts, sign-in
links, and security alerts like security.new_device_login always
deliver on their default channels. They're hidden from the preferences
catalog so there's no toggle to trip over.

