Alert Detail: Metric Reference
This page is the source of truth for the in-app Explain this panels on the alert group detail
view (/alerts/detail?code=…) and the Details block in the occurrence split panel. Each section
is written once as a content partial under _explain/alerts/detail/ and rendered both here and
inside the app's info panel (scripts/build-explain.mjs compiles the registry).
Details
Metadata for the selected alert occurrence in the split detail panel.
How it's calculated
- Fields come from the selected
AlertItemrow (engine, category, check frequency, threshold, instance/database, scope, status, created, assignee, SLA, escalation/ticket) — not a separate detail endpoint for this table. - Shown when the All Occurrences list is in split view. Description, impact, causes, and actions live in sibling panel sections; this help entry covers the Details table only.
Reading it
Use Details to confirm where the signal fired and who owns it. If the row is muted, the panel banner links to Settings — muted alerts stay out of default list KPIs until you show muted.
Occurrences
How many times this alert template code fired in the scoped window.
How it's calculated
GET /api/v1/alerts/grouped/{code}/items(viaqueryAlertsByCode) — usespagination.totalCountfor the full total.- Scoped by topbar time window and optional instance filter from the URL. The header fetch loads up to 100 rows for downstream tiles; the count itself is not capped.
Reading it
When total exceeds 100, companion tiles that uniq over loaded rows may undercount distinct databases/instances. Use All Occurrences paging for the full set.
Databases
How many distinct databases appear among the loaded occurrences for this template.
How it's calculated
- Client-side unique count of
databaseNameover the header page of occurrences (up to 100 rows fromqueryAlertsByCode). - Same time and instance scope as Occurrences. Can undercount when more than 100 rows span additional databases.
Reading it
A single-database group often shows the name in the hint. Widen the window or clear instance filters if you expect broader coverage than the tile shows.
Instances
How many distinct instances appear among the loaded occurrences for this template.
How it's calculated
- Client-side unique count of
instanceNameover the same ≤100 header rows as Databases. - Timeline bubbles use the same loaded set for the Y-axis (one series per instance).
Reading it
If Occurrences is much larger than 100, treat this as a lower bound until you page through All Occurrences.
Last triggered
The most recent trigger time among loaded occurrences for this template.
How it's calculated
- Maximum
last_triggered_at/timestampover the header occurrence page (≤100 rows). - Hint may also show the earliest trigger in that set when it differs. Header severity badge uses the worst severity across loaded rows, not only the latest row.
Reading it
Compare with the Timeline to see whether the latest fire sits in a quiet or busy cluster of buckets.
All Occurrences
Every occurrence of this alert template in the current window, with a selectable list and detail panel.
How it's calculated
- Paged
queryAlertsByCodefor the detail route'scode, using the same time range and instance scope as the header KPIs. - Opens focused on the newest occurrence. Split view shows the Details panel for the selection; the left list hides when there is only one occurrence total.
- Search is disabled on this by-code list (server search is not available here).
Reading it
Use this list for acknowledge / mute / assign / escalate on individual rows. Timeline below summarizes the same window; Details explains the selected row.
Timeline
When and where this template fired in the window — bubbles by instance over time.
How it's calculated
- Built client-side from the header occurrence page (≤100 rows), not from
GET /api/v1/alerts/history. - Each cell is instance × time bucket: size is count, color is worst severity in the cell. Bucket width follows the same history-range helper used elsewhere on Alerts.
- Caption notes when only the latest N of total occurrences are plotted.
Reading it
Placed under All Occurrences so you can jump from a dense bubble to the matching rows. Empty timeline usually means widen the time range or clear an instance filter that excluded every row.