背景
先讲一个我亲历、每次复盘都会被翻出来的场景。
凌晨 02:13,Prometheus 告警把值班同学从床上叫醒:核心网关 5xx 率从 0.2% 飙到 4%,持续 4 分钟,触发的是一条 error_rate > 1% for 3m 的规则。按团队 SOP,值班同学要做的第一件事不是「修」,而是判断:
- 这条告警是不是真的需要我半夜爬起来?还是只是上游一次重试风暴、自己会回落?
- 是不是别人已经接了?(凌晨 02:00 有个发布,发布人可能正在处理)
- 该看哪一块——网关?上游?DB?
- 该做哪个动作——重启?回滚?扩容?还是先等 5 分钟看趋势?
这一段从「告警响了」到「有人开始动手(执行第一个 runbook 动作)」的时间,我干了 15 年运维,给它起了个名字,叫分诊时间(Triage Time,TTT)。
问题是:我见过的 90% 的团队,从来没把 TTT 当过指标。
我们盯的是 MTTR——从故障开始到恢复。但 MTTR 是个「结果指标」,它把分诊、定位、修复、验证全揉在一起。一个 MTTR 15 分钟的事故,里面可能分诊就花了 11 分钟(值班同学反复被叫醒、看告警、判断要不要动),真正修复只用了 4 分钟。我们把最贵的那一段藏在了 MTTR 的尾巴里,然后抱怨 MTTR 降不下去。
常见分歧
社区里关于 on-call / 告警治理的讨论已经很多了:#123 聊 P0 里值班同学有没有权直接回滚、#608 辩 on-call 是必要的痛还是惩罚、#695 算 on-call 该不该显性定价、#850 聊告警治理的边界、#871 问 15 个服务后每周被叫醒 10+ 次怎么降。
但我发现一个大家绕着走、却没正面摆上桌的分歧——告警体系该用什么当「主指标」:
- 派 A:告警数量派。 主指标是「每周被叫醒次数」「告警/动作比」。#871 那位同学问的就是这个。逻辑:告警越少,值班同学越不累。
- 派 B:MTTR 派。 主指标是「故障平均恢复时长」。逻辑:用户只关心恢复,不关心你分诊花了多久。
- 派 C(我的倾向):TTT 派。 主指标是「告警触发 → 第一个有效动作的时间」。逻辑:分诊是 on-call 体系里唯一一段纯人力、纯认知、且不可自动化的环节。告警能降噪、MTTR 能靠自动修复拉低,但判断要不要动、动哪里这件事,在可预见的未来都得人来做。
我的倾向与理由
我站派 C,理由有三个,都是踩坑踩出来的:
- TTT 是唯一不会被「自动修复」骗掉的指标。 你上了自动重启、自动扩容,MTTR 会好看,告警数也会好看,但 TTT 不会——因为「要不要让自动修复去干」这个判断还是人做的。
- TTT 能暴露 SOP 的真实质量。 一个 runbook 写得再好,如果值班同学凌晨 3 点要翻 4 个 tab、查 3 个 dashboard 才能「知道该看哪个 runbook」,TTT 一定难看。而 MTTR 可能因为「最后自动修复兜底了」而假装好看。
- TTT 是「告警降噪」的真正验收标准。 降噪不是把 47 条规则砍到 20 条就完事,而是「剩下的 20 条,每一条响了之后,值班同学能在 30 秒内决定下一步动作」。#871 那位同学问「告警到行动比怎么算」,我猜他真正卡住的是这个:他不知道怎么给「行动」定义一个可测量的起点。
TTT 埋点落地方案(补记 2026-10-20)
写了这帖后我自己被问「埋点怎么做」,把我踩过的坑和一套能直接跑的方案补在这里,免得大家只停留在概念。
三个时间戳,缺一不可
T0 = 告警系统 firing 时间(Prometheus / Alertmanager 的 `startsAt`)
T1 = on-call 工具「认领」时间(PagerDuty `acknowledged_at` / Opsgenie `acknowledgedAt`)
T2 = 第一个 runbook 动作的「可观测锚点」
T2 是最难定义的,也是我见过最多团队翻车的点。三种做法我分别踩过:
| 做法 | 优点 | 坑 | |------|------|-----| | runbook 文档第一步的「已读」点击 | 实现最简单 | 值班同学点完「已读」就挂了,TTT 好看但啥也没干 | | 运维工单系统第一条「执行记录」 | 有审计痕迹 | 工单系统是事后补录的,T2 比实际动作晚 2~5 分钟 | | 执行网关的第一条命令日志(kubectl / terraform / 发布系统 API 调用) | 最真实,不可伪造 | 需要打通执行网关的审计日志,一次性成本最高 |
我的建议:T2 用「执行网关的第一条命令日志」,T1 用 on-call 工具的「认领」,TTT = T2 - T0。同时单独记 T1 - T0(认领时间,ATK) 作为辅助指标。TTT 是「结果」,ATK 是「过程」——TTT 好看但 ATK 也好看,说明 SOP 真的好用;TTT 好看但 ATK 难看,说明有人「先认领再慢慢想」,刷分诊了。
一组实测数据(某 12 个服务的团队,2026 Q3)
我们把 TTT 埋上去跑了 6 周,拉了 37 次 P1/P2 告警:
TTT P50 = 4 min 12 s P90 = 11 min 30 s P99 = 23 min
ATK P50 = 48 s P90 = 2 min 10 s P99 = 5 min
对比同期 MTTR:
MTTR P50 = 18 min P90 = 42 min P99 = 85 min
关键发现:TTT 占了 MTTR 的 23%~28%。也就是说,MTTR 里近 1/4 的时间是「人在判断」,而不是「在修」。更扎心的是:P99 的 TTT(23 min)比 P50 的 MTTR(18 min)还长——最贵的那次事故,人光判断就花了比平均修复还多的时间。
一个反面案例(为什么 TTT 不能当唯一 KPI)
我见过一个团队把 TTT 定成了 on-call 的唯一 KPI,结果 3 个月后出了两件事:
- 「秒认领」文化:值班同学被叫醒后第一件事是「先点认领」,TTT 从 4 min 降到 40s,但真正动手的时间没变——他们把 T1 - T0 压到了 5 秒,但 T2 - T1 反而从 3.5 min 涨到了 8 min(因为「先认领再慢慢想」)。TTT 看着好看了,但判断质量下降了——有两次因为「先认领了再慢慢看」,错过了最佳回滚窗口。
- 告警分级被绕过:为了 TTT 好看,有人把 P2 告警的 runbook 第一步改成「确认是 P2 则直接关闭」,TTT 从 6 min 降到 20s,但真正需要处理的 P2 被静默吞掉了。
教训:TTT 必须和「动作有效性」绑定——T2 不能是「点了一个按钮」,必须是「产生了一个不可逆副作用的动作」(回滚、重启、扩缩容、切流)。否则 TTT 就变成了一个「按快进键」的游戏。
防刷分的两条硬规则
- T2 必须是「不可逆动作」的日志:回滚 API 调用、kubectl delete、发布系统 rollback 端点——这类动作在审计日志里有明确的时间戳和 operator,无法伪造。
- 「认领后 10 分钟无动作」自动升级:如果 T1 之后 10 分钟内没有 T2,on-call 系统自动 escalate 到 on-call lead,同时记一条
triage_stall事件。这条规则上线后,「秒认领然后挂着」的行为从 37 次里的 9 次降到了 1 次。
想听大家怎么选
抛几个具体问题,想听不同场景下的答案:
- 你团队现在用哪个当主指标? 告警数、MTTR、还是别的?如果让你补一个 TTT,你打算怎么埋点?(告警系统的时间戳?runbook 第一步的点击?还是 on-call 工具的「认领」动作?)
- 你的 TTT 目标定多少? 我见过一个团队定 P50 = 60 秒(从告警触发到值班同学在 on-call 工具里点「认领」),另一个团队定 P50 = 5 分钟(到第一个 runbook 动作)。这两个数差 5 倍,你们觉得哪个合理?为什么?
- 凌晨 3 点和下午 3 点,TTT 该用同一把尺子量吗? 我见过一个团队把 TTT 拆成「工作日 / 夜间 / 节假日」三档,夜间目标直接放宽到 5 倍。你觉得这种「分时段 SLO」是务实还是双标?
- 如果 TTT 做成了主指标,会不会出现「刷分诊」? 比如值班同学为了 TTT 好看,把告警直接认领然后挂着不管(反正自动修复兜底)?你们见过这种副作用吗?怎么防?
先抛这几颗种子,我猜会有人站派 A 说我「把运维指标搞复杂了」,也会有人站派 B 说「用户根本不关心你分诊多久」。欢迎来辩。