On-call rotations
Who to wake, rather than which channel to shout into — rotations, covers, and an alert routing destination that keeps meaning "whoever is on call" after Monday's handover.
Alert routing answers “where does this go”. Rotations answer the question every team actually means: who.
Find them under Settings → On-call.
A rotation
A rotation is a list of people, a shift length, and a handover time in a named zone. That is all:
- Rotation order — position in the list is the order. Reordering re-plans the future, which is what dragging a name means.
- Shift length — 7 days is the usual answer; 1 gives a daily rotation.
- Handover time and zone — “09:00, Europe/London”.
- First shift starts — a calendar date. Every later boundary is derived from it, so changing it re-anchors the whole rotation.
Shift boundaries are calendar days in the rotation’s own zone, never fixed 24-hour blocks. A rotation stepped in milliseconds drifts an hour at each daylight-saving change, until the 09:00 Monday handover happens at 08:00 — or, worse, until the boundary lands on the wrong side of the handover and two people each think the other is on call.
Routing to whoever is on call
In Settings → Notifications, a routing rule’s destinations now include your rotations. Pick one and the rule sends to the person on call at the moment the alert fires. Nobody edits the rule at handover.
The on-call destination sends a push notification to that person, and it still respects their own per-trigger mutes. An organization rule decides whether the org is told; a member decides whether their phone rings. Being on call does not override that — a rotation is not a licence to bypass somebody’s own settings.
If a rotation resolves to nobody — it is off, empty, has not started yet, or could not be read — the rule’s other destinations still deliver. An alert lost to a misconfigured rotation would be the worst thing this feature could do, so it is the one thing it will not do.
Two rules that name two rotations with the same person on call this week ring that person’s phone once, not twice.
Covers
Somebody is at a wedding on Saturday. Press Arrange cover, pick who is standing in and for how long.
A cover beats the rotation for exactly its window and nothing else. Where two covers overlap, the one written most recently wins — so a later correction supersedes an earlier arrangement rather than the answer depending on which row the database returns first.
Escalation still goes to the next person in the rotation, never to whoever happens to be covering next. A cover is somebody standing in for one shift.
Permissions
Seeing who is on call needs Team: read — every member needs it and nobody should have to ask an admin.
Arranging cover also needs only Team: read. Cover gets arranged at 17:55 on a Friday, and the person handing over is rarely an org admin. Every cover is audit-logged, which is the control that makes the looser permission safe: the question a reviewer asks afterwards is “who was actually on call”, and the log answers it.
Creating or editing a rotation needs Organization settings: write. A rotation decides who gets woken up.
Leavers
Removing somebody from the organization removes them from every rotation and cancels their covers, automatically. A rotation naming somebody who has left pages nobody, silently, on their week — which is the worst failure this feature could have, so it is enforced by the database rather than by anyone remembering to check.
Not yet
There is no per-rotation escalation policy separate from the routing rule’s
own, no round-robin across two rotations, and no phone or SMS leg for the
on-call destination (the alert routing rules’ Twilio paging is org-wide, not
per-person). The next person is exposed by the API and shown in the UI, so
the escalation half is one step away.
In Terraform
A rotation is an infrawrench_on_call_schedule, and a routing rule reaches it
with a destination whose kind is on-call:
resource "infrawrench_on_call_schedule" "platform_primary" {
name = "Platform primary"
timezone = "Europe/London"
rotation_days = 7
handoff_time = "09:00"
start_date = "2026-08-03"
# The order of this list is the rotation.
participant_user_ids = [var.ada_id, var.grace_id, var.alan_id]
}
Covers are deliberately not managed in Terraform: they are arranged the morning somebody wakes up ill, and a plan that reverted one would be actively harmful. Arrange them in the app. See the Terraform provider.
Over the API
GET /api/org/{orgId}/on-call/now answers “who is on call” in one call —
useful for a status page, a Slack command or a dashboard tile. See the
OpenAPI reference.