On-Call 與告警設計#
On-Call(值班)是把 SLO 承諾落實到 24 小時防線的人力安排,而告警(Alerting)則是連接「系統異常」與「人介入」的橋樑。設計不當的值班會燒乾團隊、設計不當的告警會淹沒值班者。本章談如何用公式推算合理的值班人力、如何守護值班者的心理安全、以及如何讓每一次 page 都值得被吵醒。告警背後的監控訊號採集見 09 可觀測性,事故後的檢討見 15 無究責事後檢討。
值班的反應時間 SLO#
值班的第一要務,是約定好「多快要有人開始處理」。這個反應時間目標應由服務的 SLO 與錯誤預算 反推:
- 錯誤預算緊(高可用服務) ➡️ 要求短反應時間(如 5 分鐘內),值班者必須隨時可立即上線。
- 錯誤預算寬(容忍度高的服務) ➡️ 可接受較長反應時間(如 30 分鐘),值班壓力較小。
反應時間目標直接決定了值班的形態:要求 5 分鐘響應,就意味著值班者隨身帶裝置、不能離線;若可接受 30 分鐘,則生活彈性大得多。
值班輪值模型#
| 模型 | 說明 | 適用情境 |
|---|---|---|
| 主/副(Primary/Secondary) | 主值班先處理;主值班漏接時副值班頂上 | 單一時區團隊的標準配置 |
| Follow-the-sun | 多時區團隊接力,各自只在白天值班 | 跨國團隊,避免夜間值班 |
| 隨選(On-demand) | 平時無人專職,事故時才召集 | 低風險、低流量服務 |
Follow-the-sun 是消除夜間值班最有效的辦法:把全球團隊按時區排成接力,讓每個人都只在自己的白天值班。它的代價是需要跨時區團隊與嚴謹的交接流程。
用 25% 規則推算最少人數#
健康的值班不該讓任何人長期被綁住。常見的經驗法則是 每位工程師花在值班上的時間不超過 25%——剩下的時間用於工程與削減 toil(呼應 14 章 的 50% 工程上限)。
由此可反推單一值班輪所需的最少人數。若採「主+副」兩條值班線,且每人值班占比上限為 $25%$:
$$N_{\min} = \frac{\text{值班線數}}{\text{每人值班占比上限}} = \frac{2}{0.25} = 8\ \text{人}$$
也就是說,要維持主/副雙線值班又不讓任何人超過 25%,團隊至少需要 8 人。人數不足時,只能在「拉高個人值班占比」「減少值班線數」或「縮小值班覆蓋範圍」之間取捨。
一輪事件量上限#
值班的負荷不只看時數,更看「一個班要處理多少事件」。一個經驗上限是:每次 12 小時值班班次,需要人實際介入的事件不超過約 2 件。
道理在於:認真處理一起事故——診斷、緩解、記錄、後續寫 postmortem——需要數小時的專注。班次內事件太多,值班者根本無法妥善處理每一件,只能草草滅火。
$$\text{單班事件上限} \approx 2\ \text{件 / 12 小時}$$
如果值班者持續超過這個事件量,問題不在「值班排得不夠」,而在「系統太脆弱、告警太吵」。正確的反應是回頭修系統與告警,而不是排更多人來承受更多 page。
值班者的心理安全#
可持續的值班建立在三個支柱上:
- 明確的升級路徑(Clear escalation):值班者必須知道「我搞不定時找誰」。沒有後援的值班是孤立無援的恐慌。
- 充分的工具與文件(Playbooks/Runbooks):每個常見告警都該有對應的處理手冊,告訴值班者「看到這個 page,先做這幾步」。
- 無究責文化(Blameless):值班者必須相信「即使我處理失誤,也不會被究責」,才敢於果斷行動。這直接呼應 15 章。
升級流程#
flowchart TD
A[告警觸發] --> B[通知主值班]
B --> C{在反應時間內<br/>確認?}
C -->|是| D[主值班處理]
C -->|否| E[升級至副值班]
E --> F{在反應時間內<br/>確認?}
F -->|是| G[副值班處理]
F -->|否| H[升級至值班經理 / 召集事故指揮]
D --> I{超出能力範圍?}
G --> I
I -->|是| H
I -->|否| J[緩解並記錄]
H --> J
J --> K[事後檢討]告警設計原則#
告警的目的,是在「使用者受害」之前把對的人叫來。設計不當的告警比沒有告警更糟——它會訓練值班者忽略所有 page。核心原則:
- 每個 page 都對應一個 SLO 威脅:只有「正在或即將違反 SLO」的事,才值得把人吵醒。CPU 高、磁碟滿但不影響使用者,不該 page,最多記一筆待辦。
- 每個 page 都可行動(actionable):收到 page 的人必須有事可做。無事可做的告警只是噪音。
- 聚合與去重(aggregation & dedup):同一根因引發的數十條告警,應聚合成一條,避免值班者被同一件事轟炸。
- 症狀導向而非原因導向:對「使用者感受到的症狀」(錯誤率上升、延遲變高)告警,而非對每一個可能的內部原因告警——後者既掛一漏萬又雜訊滿天。
告警分級#
| 等級 | 觸發條件 | 通知方式 | 反應期待 |
|---|---|---|---|
| Page | 正在/即將違反 SLO,需立即介入 | 電話 / 推播,吵醒人 | 數分鐘內 |
| Ticket | 需處理但不緊急,可排程 | 工單 / IM | 數小時 ~ 隔日 |
| Logging | 僅供事後分析,無需即時動作 | 寫入儀表板 / 日誌 | 無 |
最常見的告警錯誤,是把大量「Ticket」甚至「Logging」級別的事情設成 Page。久而久之,值班者對 page 麻木,真正的 SLO 威脅反而被淹沒。寧可 page 少而精。
告警風暴與靜音#
當一個根因引發連鎖故障,告警系統可能在幾秒內噴出成百上千條 page——這就是告警風暴(alert storm)。應對手段:
- 依賴抑制(inhibition):當上游的「資料庫不可用」告警觸發時,自動抑制所有下游「服務連不上資料庫」的衍生告警。
- 分組(grouping):把同一服務、同一原因的告警合併成單一通知。
- 靜音(silencing):在計畫性維護或已知事故處理期間,主動把相關告警靜音一段時間,避免重複轟炸值班者。
- 節流與抑制重複(throttling / repeat interval):同一條告警不在短時間內反覆通知。
Prometheus 告警規則範例#
以下示範一條「症狀導向、對應 SLO、可行動」的告警,搭配 Alertmanager 的聚合與抑制:
# prometheus rules:對使用者症狀告警,而非對內部原因
groups:
- name: checkout-slo
rules:
# 高燃燒率:短窗口捕捉突發大故障(呼應第 13 章 burn rate)
- alert: CheckoutErrorBudgetFastBurn
expr: |
(
sum(rate(http_requests_total{route="/checkout",status=~"5.."}[5m]))
/
sum(rate(http_requests_total{route="/checkout"}[5m]))
) > (14.4 * (1 - 0.999))
for: 2m
labels:
severity: page # 對應 SLO 威脅,吵醒人
annotations:
summary: "結帳錯誤預算快速燃燒,2 小時內將耗盡當月預算"
runbook: "https://runbooks.internal/checkout-error-budget"
# 低燃燒率:長窗口捕捉緩慢滲漏
- alert: CheckoutErrorBudgetSlowBurn
expr: |
(
sum(rate(http_requests_total{route="/checkout",status=~"5.."}[1h]))
/
sum(rate(http_requests_total{route="/checkout"}[1h]))
) > (3 * (1 - 0.999))
for: 15m
labels:
severity: ticket # 不緊急,排程處理
annotations:
summary: "結帳錯誤率緩慢偏高,需排查"# alertmanager:聚合、去重、依賴抑制
route:
group_by: [service, alertname] # 同服務同類告警聚合
group_wait: 30s
group_interval: 5m
repeat_interval: 4h # 避免短時間重複轟炸
routes:
- matchers: [severity="page"]
receiver: oncall-pager
- matchers: [severity="ticket"]
receiver: ticket-queue
inhibit_rules:
# 上游 DB 掛掉時,抑制所有下游「連不上 DB」的衍生告警
- source_matchers: [alertname="DatabaseDown"]
target_matchers: [alertname="ServiceCannotReachDatabase"]
equal: [cluster]小結#
- 反應時間 SLO 由服務的錯誤預算反推,並決定值班的形態。
- 25% 規則推算最少值班人數(主+副雙線、上限 25% ➡️ 至少 8 人);單班事件上限約 2 件。
- 心理安全靠明確升級路徑、充分文件與無究責文化三者支撐。
- 每個 page 都該對應 SLO 威脅、可行動、經過聚合去重;用抑制與靜音對抗告警風暴。