故障不可避免,关键是多快恢复
做运维的都希望系统永远不出事,但 SRE 这个领域的第一课恰恰相反:故障是一定会发生的,追求「零故障」既不现实、也会把团队压得不敢变更。真正该追求的,是出了事之后多快能恢复——用户感受到的影响,是「故障持续了多久」,而不是「有没有故障」。
所以这一篇不讲怎么把系统做到永不宕机,而是讲出了问题怎么把影响压到最小、怎么从每次故障里学到东西、怎么让下一次更快。这就是 SRE 的核心:不是消灭故障,是把故障的代价一次次压低。
用户不在乎你有没有备份,在乎的是你花了多久把它恢复。
- MTTR把恢复时间拆成几段,分别优化。
- 告警分级别把半夜的每一次告警都当成真正的故障。
- 先止血故障中优先恢复,再慢慢定位根因。
- 复盘对事不对人,把教训变成制度。
MTTR:把故障拆成几段来盯
MTTR(平均恢复时间)是 SRE 最核心的指标之一,但光看一个总数没用,得拆开:
MTTR = MTTD 发现时间
+ MTTA 响应时间(人接到告警并开始动手)
+ MTTF 定位+止血时间
+ MTTV 验证恢复时间
很多团队盯着「恢复要多久」,其实瓶颈不在定位,而在前面两段——告警响了二十分钟才有人看,或者值班的人不知道该干嘛。把这几段分别计时,你才知道该优化哪里:是告警太晚(监控没覆盖)?是响应太慢(没人值班)?还是定位太久(日志找不到)?每一段对应不同的改进动作。
值班与告警:别让半夜的电话白响
告警这东西,响得多了人就麻了。一个被半夜叫醒十次、其中九次是误报的值班工程师,第十次真故障来的时候反而会觉得「又是误报,再睡会儿」——这就是告警疲劳,最危险的状态。
解法是分级:P0 真故障(影响线上用户)才打电话叫人;P1 影响小一点,发个群消息白天处理;P2 只是需要关注的指标波动,记录下来别打扰人。配合前面讲的监控告警体系,每一级告警都要问一句:这条告警叫醒了人,是真的需要人立刻动手吗?不需要的就降级,别浪费值班人的睡眠。
故障响应流程:发现、止血、定位
真故障来了,现场容易乱。提前定好一个标准流程,按顺序走:
第一步:发现与定级
- 谁先发现的?影响多大?定 P0/P1/P2
第二步:拉起响应群
- 值班人 + 相关服务负责人进一个群,统一信息
第三步:止血(见下一节)
- 先把用户影响止住,别死磕根因
第四步:记录时间线
- 几点发现、几点止血、几点恢复,全记下来
第五步:恢复确认
- 监控指标回到正常再宣布恢复
这个流程的关键是有人统一指挥——故障现场最怕一堆人各自动手,越帮越忙。值班负责人负责协调,其他人按分工查日志、查监控、准备回滚。
先止血后定位:别在故障中较劲
这是 SRE 里最反直觉、也最重要的一条:故障进行中,优先恢复,不要执着于当场找到根因。很多团队出问题后,一群人围着日志分析了两小时才想起来回滚——用户已经多疼了两小时。
止血手段一般就那几招:回滚到上一个稳定版本、切流量到备用集群、重启挂掉的服务、限流挡住一部分请求。先用这些手段把用户影响止住,根因留给复盘阶段慢慢查。记住:根因再清楚,用户已经多等的那两小时也回不来了。
复盘:对事不对人
故障恢复之后,复盘(postmortem)是把这次故障变成团队资产的关键一步。但很多复盘做成了「追责大会」,谁出错谁挨骂——结果就是下次故障大家都藏着掖着,没人敢说真话。
好的复盘有几个原则:对事不对人,不问「谁干的」,问「系统和流程哪里出了问题」;写清楚时间线,几点发生、几点止血、根因是什么;列出改进项,每一项都要有责任人和 deadline。相信一个前提:只要系统设计得让一个普通人都能犯的错,它迟早会犯。复盘要改的是系统,不是去怪那个犯错的人。
把复盘结论变成制度
复盘写完就束之高阁,是最常见的浪费。真正有效的是把每一条改进项都落到具体动作上:
复盘改进项示例:
- 这条告警半夜没人接 → 改值班排班,加二线值班
- 回滚忘了怎么做 → 把回滚步骤写成 runbook,贴在响应群置顶
- 日志没记到这一跳 → 补一条埋点,下次故障能看到
- 这次定位花了两小时 → 加一个监控面板,下次一眼能看到
这么做一段时间你会发现:同样类型的故障,第二次发生时恢复明显更快了。因为上次踩的坑已经变成了 runbook、变成了监控面板、变成了自动告警。SRE 的成熟度,就是这么一次一次从故障里长出来的。别害怕故障——害怕的是同一个坑踩两次。