Alert routing service with silences and escalation
I was asked this
No reports yet. Sign in to say where you were asked it.
Build the routing core of an alerting service. The monitoring system calls fire(labels, now) for an active alert on every evaluation cycle (every 30 seconds or so) and resolve(labels, now) once when it clears. Your router decides who gets notified. Every method takes the current time; time never goes backwards. Methods return the notifications to send as (receiver, kind, fingerprint) tuples, where fingerprint is the alert's labels sorted by key and joined as k=v with commas.
Part 1: routing. Routes are an ordered list of {"match": {label: value}, "receiver": str, "continue": bool}. An alert matches a route when every matcher equals the alert's label. The first matching route wins; if it has continue: true, keep walking and collect more receivers. No match: the default receiver. Implement route(labels) -> [receiver] (no duplicates).
Part 2: dedupe and resolve. fire notifies each receiver (kind = "firing") unless that receiver already heard about this alert less than repeat_interval seconds ago. Label order must not matter. resolve sends "resolved" only to receivers that were notified, then forgets the alert; resolving an unknown alert sends nothing.
Part 3: silences, ack, escalation. silence(matchers, start, end) -> id mutes matching alerts while start <= now < end; expire_silence(id) ends one early. An empty matcher set is rejected. A route may have "escalate": {"after": seconds, "to": receiver}: tick(now) pages to once (kind = "escalated") if the alert is still active, not acked and not silenced, after seconds after its first notification. ack(labels) stops escalation. Escalation receivers also get the resolve.
class AlertRouter:
def __init__(self, routes: list, default_receiver: str, repeat_interval: int): ...
def route(self, labels: dict) -> list: ...
def fire(self, labels: dict, now: int) -> list: ...
def resolve(self, labels: dict, now: int) -> list: ...
def silence(self, matchers: dict, start: int, end: int) -> int: ...
def expire_silence(self, silence_id: int) -> bool: ...
def ack(self, labels: dict) -> bool: ...
def tick(self, now: int) -> list: ...
Sign in to see the worked answer
The full answer, chapter by chapter, with what interviewers expect at each level. Free with an account: one full answer per company.
What the labs asked this week
A weekly email of what OpenAI, Anthropic and the other top AI labs asked engineers, round by round.
Sign in to see the worked answer
The full answer, chapter by chapter, with what interviewers expect at each level. Free with an account: one full answer per company.
Sign in to submit your code; every attempt is kept here.
