想象李家为了让日子既有烟火气又不失控,定了一条家规:每月最多允许十次“大糟心事”,比如孩子发烧、水管漏水、车抛锚。只要这个月的“糟心额度”还在,他们就可以继续尝试露营、长途旅行等有风险的安排;一旦额度见底,全家就自动切换到低风险模式。SRE 里的 Error Budget 错误预算,就是这本月度“容错账本”。服务的可靠目标不是 100%,而是 99.9% 这类可接受的底线;底线之外留下的 0.1%,就是允许出错的预算。账本不会说谎:剩余预算多,团队可以更快发布;剩余预算少,团队应该停下来修稳定性。这篇文章就像一个家庭账本使用指南,带你理解如何计算、监控并花好这 0.1% 的容错空间。
掌握错误预算,你就能把可靠性从“感觉”变成“账本”,用数据驱动发布、告警和团队协作,这是 SRE 的基本功。
可视化演示
展示Error Budget三模式:预算计算(SLI→SLO→EB三层关系+EB%/T_ERR/BURN/CONS公式+预算消耗进度条OK/WARN/FREEZE三阈值+99%-99.999%四级SLO)、多窗口告警(燃烧率时间线+P1 14x/P2 6x/T 3x三阈值+1H/5M/6H/1D四窗口+多窗口多燃烧率告警规则)、发布策略(NRM正常/RST限制/FRZ冻结三阶段+发布节奏时间线+REL/REV/CAN/BLK四决策矩阵+速率/稳定/创新/风险平衡指标)。
本节配有交互动效(进入视口后自动加载,约 3KB)。
SLI→SLO→Error Budget三层计算 SLI服务质量指标→SLO 99.9%目标→EB 0.1%错误预算=30天43分钟 预算消耗进度条:OK(80%)三阈值 EB = (1 - SLO) × Window 剩余65%,燃烧率3.5,窗口30天
错误预算定义
李家立下的“糟心额度”不是拍脑袋定的,而是先把“一家人想要的安全感”写下来。他们不追求永远不出事,只追求大事不出格、小意外能被接住。这就像 SRE 不追求 100% 可用,而是先定一个可靠底线,也就是 SLO。SLO 是向用户承诺的“可靠等级”,比如这个月 99.9% 的请求都要成功。剩下的 0.1%,就是错误预算。
从家庭账本过渡到技术术语:SLO 是承诺,错误预算则是承诺之外留出的容错空间。两者的关系非常简单,可靠底线加上容错空间,必须等于 100%。如果承诺越高,容错空间就越小;如果承诺越低,容错空间就越大。SRE 用这个互补关系把“可靠性”这个抽象概念,变成了每个月可以量化、可以被消耗、可以被监控的数字。
在监控系统中,SLI 是实际测量出来的指标,比如请求成功率、延迟达标率。SLO 是根据 SLI 定下的目标,而错误预算就是 1 减去 SLO。假设某服务 SLO 是 99.9%,那么错误预算是 0.1%。如果本月有 1000 万次请求,最多可以允许 1 万次失败;如果按时间算,一个月大约允许 43 分钟不可用。错误预算一旦被设定,团队就可以围绕它建立发布门禁和告警规则。
最后再回到李家的冰箱。他们把“每月十次糟心事”写在最醒目的地方,SRE 则把“错误预算还剩多少”放在监控大屏上。只要额度还没花完,大家就能安心尝试新事物;一旦额度见底,所有人都知道该收手了。
- SLO 可靠目标这是团队向用户承诺的可用性等级,比如 99.9%。
- 互补关系可靠承诺之外的剩余比例,就是可以接受的故障上限。
- 错误预算这个 0.1% 就是本月的容错额度。
预算计算方法
李家记账的第一步,是搞清楚这个月到底有多少钱可以被“糟心事”花掉。这个数字不是固定的,它取决于两件事:家庭本月的活动总量,以及全家能接受多大比例的计划外风险。对应到 SRE,就是总请求量和容错比例。总请求量越大,在同样的 SLO 下,允许失败的绝对次数就越多;容错比例越高,错误预算也越宽裕。
把记账逻辑翻译成监控指标:错误预算的绝对数量,应该用“总请求量乘以容错比例”来计算。容错比例就是 1 减去 SLO。例如 SLO 是 99.9%,容错比例是 0.001;如果本月总请求量是 1000 万,允许失败量就是 1 万次。当 SLO 是延迟类指标时,思路也完全一样:那些延迟超过阈值的请求,就是账本里的“坏账”,同样占用了错误预算。
实际工作中,错误预算通常按一个周期计算,比如一个月或一个季度。团队先把周期内的总请求量统计出来,再乘以容错比例,得到本周期“最多能坏多少笔”。之后每发生一次 5xx 错误、超时或超延迟响应,就从预算里扣一笔。这样,团队不仅能回答“现在系统好不好”,还能回答“这个月还能承受多少坏情况”。
李家月底对账时,不会只看“还剩多少钱”,而会看每一笔支出的来龙去脉。SRE 也一样,错误预算不仅是一个总数,更是由一次次失败请求累计出来的消费记录。只要把账记清楚,团队就能随时回答“容错额度还剩多少”。
- 总请求量一个计算周期内用户发出的全部请求数,这是账本的交易总量。
- 容错比例SLO 没有覆盖到的部分,用 1 减去 SLO 表达。
- 允许失败量把总请求量乘以容错比例,得到本月最多能坏多少笔。
预算消耗速率
李家不会等到月底才看账本,他们会每天都问一个问题:这个月的“糟心额度”是按计划花,还是花得太快?如果十天就把额度用掉了一半,后面二十天就只能躲在家里不出门。这个“花钱速度”,就是 SRE 里的燃尽率 Burn Rate。燃尽率回答的不是“还剩多少”,而是“按这个速度还能撑多久”。
燃尽率的计算逻辑是:用实际错误率除以可容忍错误率。可容忍错误率就是 1 减去 SLO。如果实际错误率和可容忍错误率相等,燃尽率等于 1,说明预算正按计划消耗;如果实际错误率是可容忍错误率的两倍,燃尽率等于 2,说明预算会以两倍速度烧完;如果燃尽率是 0.5,说明系统比预期更稳定,预算消耗得很慢。
举个例子:SLO 是 99.9%,可容忍错误率是 0.1%。某天实际错误率达到 0.2%,燃尽率就是 2。如果这不是偶发峰值,而是一直持续,那么 30 天的预算大约会在 15 天左右耗尽。SRE 通常会用短窗口观察突发,用长窗口观察慢性消耗,避免被瞬时抖动欺骗。
李家的经验是:余额下降不可怕,可怕的是下降速度越来越快。燃尽率就是那个“速度计”。当速度超过红线时,哪怕账面上还有钱,也要提前踩刹车,而不是等归零后再行动。
- 实际错误率统计窗口内失败请求占总请求的比例,来自监控的 SLI。
- 可容忍错误率1 减去 SLO,也就是错误预算占全部请求的比例。
- 计算燃尽率用真实消耗速度除以计划消耗速度。
开发节奏管理
当李家额度过半时,他们仍然会去爬山、露营,因为这些冒险带来的快乐值得承受风险;可当额度只剩 10% 时,他们连新滑板都不敢买。服务的发布节奏也是如此。错误预算就是 SRE 手里的“开发节奏开关”:预算充裕时,团队可以大胆上线新功能;预算紧张时,团队应该主动收缩,把重心从“新增价值”切换到“保住稳定”。
在实际开发流程中,错误预算可以成为发布门禁的一部分。一次高风险发布,比如大版本升级、数据库迁移、模型替换,上线前先看剩余预算。如果剩余预算高,团队可以按正常流程评估后发布;如果剩余预算低于阈值,比如不足 20%,就进入稳定性冻结期。冻结期间不是所有人停摆,而是只允许低风险修复,比如配置调整、容量扩容、日志增强,不再引入新的不确定性。
这里要特别留意:错误预算没有“自动恢复”机制,它只会在下一个周期重置。想要让剩余预算变多,唯一办法是减少故障,而不是等待。冻结期结束的信号,不是“团队后悔了”,而是“故障率降下来了”。当系统重新回到稳定状态,燃尽率回到 1 以下,开发节奏再逐步恢复。
李家会为不同的“冒险项目”设不同门槛:骑车摔跤可以,带病开车不行。SRE 也一样,发布门禁的松紧应该由错误预算决定。预算充足时,门开大一点;预算紧张时,门关小一点。门禁不是阻碍创新,而是保护最后一个额度不被冲动耗尽。
告警策略设计
李家的预警器不能设计成“只要家里有任何小意外就响”,否则一天响二十次,最后大家会直接把它关掉。好的预警器应该只在两种情况响:要么突发风险太大,要么风险正在持续消耗额度。SRE 的告警策略也一样,不能只盯着剩余预算,因为等剩余预算归零再报警,系统已经出事了。
错误的告警方式只看“剩余预算百分比”,这样的指标有滞后性。更好的方式是多窗口、多速率告警:短窗口关注突发,比如过去 1 小时内燃尽率过高;长窗口关注慢性消耗,比如过去 6 小时或 24 小时,燃尽率虽然不高,但一直大于 1,预算正在被慢慢烧光。只有当某个窗口的燃尽率持续超过阈值时,才触发分页告警。
以 30 天预算窗口为例,如果 1 小时内就消耗了 2% 的预算,对应的燃尽率大约是 14.4,说明系统正在经历严重故障,要立刻叫醒值班人。如果只是偶发一次抖动,持续时间很短,就不该打扰任何人。这就是多窗口设计的价值:既能对突发快速响应,又能对“温水煮青蛙”式的慢性消耗保持敏感。
李家的预警器只在“概率高、后果重”的时候响,SRE 的告警也一样。多窗口设计让告警既不过度灵敏,也不过度迟钝。报警不是目标,让团队在错误预算彻底烧完之前采取行动,才是目标。
- 燃尽率超过 1说明当前消耗速度已经比“按计划花完”更快。
- 持续时间要足够设置一个时间阈值 τ,用来过滤瞬时噪声。
- 同时成立当二者都为真,才升级为告警,避免打扰值班人。
可靠性与创新平衡
李家如果要求“一次糟心事都不许发生”,那他们只能整天待在家里,什么新鲜事都不做。可靠性与创新天然存在张力:为了多一个 9 的可用性,团队要付出更多冗余、监控和运维成本,而换来的用户体验提升却越来越小。错误预算的价值,就是把这笔账摆到桌面上,让团队诚实地回答:我们愿意用多少容错空间,换取多少发展速度。
从 99.9% 提升到 99.99%,听起来只是多了一个 9,实际上允许故障时间从每月约 43 分钟缩短到约 4 分钟。为了实现这 39 分钟的差距,可能需要多机房容灾、更复杂的自动恢复、更昂贵的架构设计。这种投入指数级增长,但用户可能根本感知不到差别。因此,SLO 定多少,应该是一个产品决策,而不是工程师追求完美的技术决策。
错误预算还有一个更关键的作用:它把“风险”变成可管理的资源。预算花得快,说明这阶段的风险选择过于激进;预算一直花不完,说明目标可能定得太松,团队其实可以更大胆。理想状态不是永远不出错,而是错误预算被有意识地使用,并在周期结束时刚好接近耗尽。这样,每个错误预算都用在了产品创新和用户价值上。
李家最终发现,幸福不是“永远不倒霉”,而是在可承受的风险里活得丰富。服务也一样,可靠性的终点不是 100%,而是在用户可接受的范围内,让团队跑得更快、试得更多。错误预算就是那把守住边界的尺子。
- 从 99.9% 到 99.99%可用性承诺每多一个 9,系统要消除的故障时间就少一个数量级。
- 边际成本为多出的 0.09% 可用性要付出的冗余、监控、运维成本。
- 远大于越接近完美,追加投入的收益越低,代价越高。
落地文化实践
再好的账本,如果家里只有一个人认,也执行不下去。李家的家规之所以有效,是因为全家都同意这套规则,并且知道它不是为了惩罚某个成员,而是为了共同目标。错误预算文化也是这样:SRE、开发团队、产品经理,甚至业务方,都要认同“这本账”的权威性,并愿意按它做决定。
在实际落地时,SRE 不再单方面说“不行”,而是和开发一起看剩余预算:如果预算充足,风险变更得到批准;如果预算不足,大家共同接受冻结安排。错误预算因此变成一种沟通语言,减少“SRE 阻碍创新”和“开发破坏稳定”的对立。团队复盘时,重点也不是追责某次改动,而是分析为什么燃尽率会突破预期、监控窗口是否覆盖到位、下次如何更早发现。
从用户视角看,错误预算其实是在回答一个问题:用户是否能明确感知到这次故障?如果用户完全无感,说明 SLO 可能太严;如果用户已经大量流失,说明 SLO 可能太松。每一个错误预算消耗,都应该能够回到“对用户体验的实际影响”上。这样,错误预算才不会沦为内部数字游戏。
李家的冰箱贴写着“十次额度,全家共守”;SRE 团队的文化则应该是“错误预算,共同负责”。一旦所有人都把账本当默认决策依据,发布、告警、复盘就不再靠嗓门,而是靠数据。这才是错误预算从工具走向文化的真正意义。
AI 应用场景
大模型推理服务的发布门禁
阶段:模型部署与 MLOps
解决的问题:传统方式只看离线评估指标,模型上线后是否变差要等线上投诉才知道;AI 团队经常在“要不要发布新模型”上争吵,缺少统一标准。
具体案例:一个 LLM API 服务设定 SLO 为 99.5% 可用,错误预算为 0.5%。新模型灰度期间,在线推理错误率上升到 1%,燃尽率达到 2,1 小时内就消耗了远超预期的预算。发布门禁自动拦截,SRE 与算法工程师一起回滚,先恢复稳定性再重新评估。
智能客服系统的坏回答监控
阶段:在线服务监控与可观测性
解决的问题:智能客服的错误不只有 5xx,还包括“答非所问”和“无法解决问题”,但这些语义错误很容易被传统监控漏掉。
具体案例:团队把“转人工率”和“无答案率”纳入错误预算。每一天,系统 API 错误和低质量回答都会消耗预算;当剩余预算低于 20%,新知识库更新和话术调整全部冻结,直到燃尽率回落到正常水平。
推荐系统的实验治理
阶段:A/B 实验管理
解决的问题:大量推荐策略实验同时上线,虽然单个实验风险不大,但叠加起来会让用户体验持续下降,团队却无法量化总风险。
具体案例:推荐团队把每周的“用户体验损失”折算成错误预算,每个新的候选策略都要预估预算消耗。预算充足时,实验通道开放;预算逼近红线时,只保留最有价值的实验,其余自动暂停。这样,创新速度被控制在一个可承受的范围内。
Python 演示
#!/usr/bin/env python3# Simulate a 30-day error budget ledgerimport math SLO = 0.999TOTAL_DAYS = 30REQUESTS_PER_DAY = 1_000_000 total_requests = REQUESTS_PER_DAY * TOTAL_DAYSerror_budget_count = int(total_requests * (1 - SLO))remaining = error_budget_countlow_threshold = error_budget_count * 0.2 print("total requests:", total_requests)print("error budget:", error_budget_count)print("low budget threshold:", low_threshold) for day in range(1, TOTAL_DAYS + 1): failure_ratio = 0.00105 + 0.0004 * math.sin(day / 4) failed = int(REQUESTS_PER_DAY * failure_ratio) remaining -= failed daily_error_rate = failed / REQUESTS_PER_DAY burn_rate = daily_error_rate / (1 - SLO) print(f"day {day:2d}: failed={failed:4d}, burn_rate={burn_rate:.2f}, remaining={remaining:6d}") if remaining < low_threshold: print(" -> freeze high-risk releases")
error_budget_count = int(total_requests * (1 - SLO))在 30 天窗口里把 SLO 之外的 0.1% 转成具体失败次数。remaining -= failed每一笔失败都要从账本里扣掉,这就是“消费”动作。failure_ratio = 0.00105 + 0.0004 * math.sin(day / 4)模拟真实波动,某些日子的错误率会超过允许值。burn_rate = daily_error_rate / (1 - SLO)计算当天燃尽率是否大于 1。if remaining < low_threshold:当剩余预算低于阈值,自动触发“冻结高风险发布”门禁。
常见误区
误区很多初学者认为 SLO 越高说明系统越可靠,所以应该把 SLO 定为 99.999% 甚至 100%,这样用户满意度最高。
正解SLO 越高,错误预算越小。100% 的 SLO 意味着零错误预算,任何一次发布都可能破坏承诺,团队会被“完美”锁死,完全不敢创新。就像李家要求“一次糟心事都不许发生”,那全家只能躺在家里。错误预算的意义不是让可靠性无限高,而是在可接受的风险和开发速度之间找平衡。
为何常见:人天生倾向“越多越好”,但没有意识到可靠性是有代价的,而且越接近 100%,边际成本越高。
误区有些团队看到错误预算还剩很多,就觉得自己做得非常好,甚至把“预算剩余率”当成季度 KPI。
正解错误预算一直花不完,可能说明 SLO 定得太松,团队本可以支持更多发布和实验。错误预算的本质是“可承受的风险额度”,把它完全存起来不用,等于放弃了创新机会。理想状态是预算被有计划地使用,在周期内接近合理耗尽。
为何常见:大家习惯把“没出问题”等同于“做得好”,却忽略了为了不出问题而错过的产品价值。
误区初学者以为错误预算就是“还剩多少直接看多少”,只有当预算变成 0% 时才需要进入紧急状态。
正解预算耗尽本身就是一次事故,而不是事故的预警信号。真正专业的做法是用燃尽率主动观察消耗速度,在预算还剩 20% 或燃尽率持续大于 1 时就启动门禁。就像李家不会等十次糟心事全部发生后才反思,而是在第 7 次、第 8 次时就开始减少冒险。
为何常见:因为剩余预算是一个滞后指标,它只反映“已经花了多少”,无法反映“正以多快的速度花掉”。
误区团队给监控配置了非常敏感的规则,只要错误率超过目标一点点,就给所有人发分页,结果值班人员经历大量误报。
正解告警要区分突发和慢性消耗,还需要设置持续时间阈值。多窗口燃尽率告警的目标是过滤瞬时噪声,让告警只发生在预算可能被快速耗尽或被持续消耗的场景。否则,告警疲劳会让真正重要的信号被淹没。
为何常见:初学者把“告警”当成“关注度”,以为告警越多越安全,却忘了告警成本本身也会消耗团队的精力。
误区部分开发同学认为错误预算属于运维监控范畴,开发只负责写功能,发布决策由 SRE 单方面决定。
正解错误预算要成为跨团队决策语言,必须让开发、产品和 SRE 共同认可。开发知道哪些风险变更可能消耗预算,产品知道容错空间应该给哪些功能,SRE 负责把账目讲清楚。只有共同认账,发布门禁和稳定性冻结才不会是“对立”,而是共同计划的一部分。
为何常见:传统职责划分让开发关注功能、SRE 关注稳定,忽略了可靠性本质上是产品全流程共同承担的风险。
面试题
Q1. 错误预算最接近下列哪个比喻?
- A.家庭允许发生的糟心事额度← 正确答案
- B.每月可以花完的现金余额
- C.服务器硬件的采购预算
- D.团队加班时长的计划表
答案:A。错误预算不是“钱要怎么花”,而是“用户可接受的故障容错空间”。它像李家每月允许发生的糟心事额度,用来衡量还能承受多少风险。现金余额、硬件采购和加班时长都偏离了“可靠性风险”的本质。
Q2. 若 SLO 为 99.9%,错误预算比例是多少?
- A.0.1%← 正确答案
- B.1.0%
- C.10%
- D.99.9%
答案:A。错误预算等于 1 减去 SLO。99.9% 的可靠承诺意味着最多允许 0.1% 的故障比例。1.0% 对应 SLO 99%,10% 对应 SLO 90%,99.9% 则是错误预算为零的誤解。
Q3. 错误预算的“剩余预算”意味着什么?
- A.本月还能承受多少故障← 正确答案
- B.故障已经占用的时间
- C.团队剩余的开发工时
- D.系统当前的请求量
答案:A。剩余预算是一个前瞻性指标,表示在周期结束前还能承受多少失败。故障已经占用的时间是“已消耗预算”,不是剩余预算;剩余预算与开发工时和请求量没有直接关系。
Q4. 当 Burn Rate 等于 2 时,说明什么?
- A.预算消耗速度是计划的 2 倍← 正确答案
- B.系统可用性正好为 2%
- C.本月故障时长超过 2 小时
- D.团队应把 SLO 改成 98%
答案:A。燃尽率是实际错误率除以可容忍错误率。等于 2 表示实际消耗速度是计划的两倍,按此速度预算会提前一半时间用完。它并不表示可用性为 2%,也不等于故障绝对时长。
Q5. 错误预算还剩 80%,最恰当的做法是?
- A.正常评估风险后继续发布← 正确答案
- B.立即冻结所有版本发布
- C.删除监控指标减少告警
- D.把 SLO 调高到 99.99%
答案:A。剩余预算充足时,团队可以维持正常发布节奏,但仍要做风险评估。立即冻结适合预算极低时;删除监控和修改 SLO 都是掩盖问题,不是正确处理方式。
Q6. 预算只剩 10% 时,哪些动作是合适的?
- A.只允许低风险修复和复盘← 正确答案
- B.安排稳定性专项保障← 正确答案
- C.继续上线大批新功能
- D.开发与 SRE 共同商议← 正确答案
答案:ABD。预算很低时应进入稳定性冻结,只做低风险修复,同时安排稳定性专项,并让开发和 SRE 共同商议后续动作。继续上线大批新功能会进一步消耗预算,属于错误做法。
Q7. 30 天预算窗口内,1 小时烧掉 2% 预算,对应燃尽率约为?
- A.14.4 倍← 正确答案
- B.2.0 倍
- C.0.02 倍
- D.720 倍
答案:A。1 小时占 30 天总时长的 1/720;2% 的预算在 1 小时内消耗,相当于预算会在 50 小时内耗尽,而计划是 720 小时耗尽,所以燃尽率为 720÷50≈14.4。
Q8. 多窗口告警比单一窗口更好的原因是?
- A.可区分突发与慢性消耗← 正确答案
- B.可以完全免除告警
- C.无需再计算错误预算
- D.只关注长窗口即可
答案:A。短窗口能捕捉瞬时高峰,长窗口能发现燃尽率长期大于 1 的慢性风险,两者互补,让告警既有及时性又不至于过度敏感。多窗口并不能免除告警或跳过预算计算。
Q9. 错误预算低于阈值时,哪些做法符合 SRE 原则?
- A.冻结高风险版本← 正确答案
- B.立即追责开发团队
- C.安排稳定性专项← 正确答案
- D.调低 SLO 掩盖风险
答案:AC。预算低时应冻结高风险版本,并安排稳定性工作恢复系统。追责会让团队不敢暴露问题,调低 SLO 则是用修改目标掩盖实际风险,都不符合错误预算文化的初衷。
Q10. 关于 Error Budget 的正确理解有哪些?
- A.它是可靠性与开发速度的折中← 正确答案
- B.它牺牲可靠性换取开发速度
- C.它用于指导发布和告警决策← 正确答案
- D.它让团队用数据代替争吵← 正确答案
答案:ACD。错误预算确实是可靠性与开发速度之间的一种折中,也是发布门禁和告警策略的依据,还能让 SRE 与开发用数据沟通。但它不是单方面牺牲可靠性,而是在用户可接受范围内合理冒险。