本章介绍如何在发生重要事件时将SLO转换为可进行配置的报警。我们的第一本SRE和本书都讨论了实施SLO。我们相信,拥有好的SLO可以衡量你平台可靠性,正如你的客户所经历的那样,可以为on-call人员该如何迅速做出响应提供最准确的提示。在这里,我们提供了有关如何将这些SLO转换为报警规则的具体指导,以便你在消耗过多的错误预算之前响应问题。
我们的示例展示了一系列报警指标和逻辑的复杂实现;讨论他们的功能和缺点。虽然我们的示例使用的是简单的request-driven服务和Prometheus语法,但你可以应用到任何报警框架中。
报警注意事项
为了从服务质量指标(SLI)和错误预算生成报警,需要一种方法将这两个元素组合成一个特定的规则。 你的目标是通知重大事件:消耗大部分错误预算的事件。
在评估报警策略时,请考虑以下属性:
精确度
检测到的事件比例很重要。 如果每一个报警对应一个重大事件,则精度为100%。请注意,报警可能会在低流量时段对非重要事件变得特别敏感(在第86页的“低流量服务和错误预算报警”中讨论)。
召回率
检测到重大事件的比例。如果每一个重要事件都会发出一次报警,则召回率为100%。
检测时间
在各种条件下发送报警通知需要多长时间。较长的检测时间会对错误预算产生负面影响。
恢复时间
解决问题后报警会持续多长时间。较长的恢复时间可能导致混淆或问题被忽略。
重大事件的报警方法
为SLO构建报警规则可能会变得非常复杂。在这里,我们提出了六种方法来配置重要事件的报警,以提高精度,得到一个可以同时控制精度、召回、检测时间和恢复时间这四个参数选项。以下每种方法都解决了不同的问题,有些方法最终同时解决多个问题。
前三个不可行的方法对后三个可行报警策略的应用是十分有益的,方法6是最可行和最强烈推荐的选择。第一种方法实现简单但不充分,而最佳方法提供了一个完整的解决方案,可以在长期和短期内保护SLO。
出于本节讨论的目的,“错误预算”和“错误率”适用于所有SLI,而不仅仅是名称中包含“错误”的SLI。在第20页的“测量内容:使用SLI”一节中,我们建议使用SLI来捕获正常事件与总事件的比率。错误预算给出允许的错误事件的数量,错误率=错误事件/总事件的比率。
1. 目标错误率≥SLO阈值
对于最简单的解决方案,你可以选择一个小的时间窗口(例如,10分钟),并在该窗口内的错误率超过SLO阈值时发出报警。
例如,如果SLO在30天内为99.9%,则在前10分钟的错误率≥0.1%时发出报警:
1 |
|
当最近的错误率等于SLO时发出报警意味着系统检测到以下预算消耗:
1 |
|
图5-1 显示了设有10分钟报警窗口和99.9%SLO示例服务的检测时间和错误率之间的关系。
优点 | 缺点 |
---|---|
检测时间良好:总停机时间为0.6秒(10600.1%, 10:分钟;60:秒;0.1%:上文所计算得到的10分钟的平均值)。 | 精度很低:报警会触发许多不会威胁SLO的事件。10分钟的0.1%错误率会发出报警,而每月错误预算仅消耗0.02%。 |
此报警会触发任何威胁SLO的事件,表现出良好的召回率。 | 极端情况下,你每天最多可以收到144个报警,即使不需要对此采取任何措施,并且服务仍然符合SLO |
2. 增加报警窗口
我们可以通过更改报警窗口的大小重新构建前面的示例,以提高精度。 通过增加窗口大小,你可以在触发报警之前消耗更高的预算。
为了保持报警的数量可控,你决定仅在事件消耗30天错误预算的5%(一个36小时的窗口)时才收到通知 :
1 |
|
现在,检测时间是:
表5-2 显示了在较大的时间窗口内错误率过高时发出报警的好处和缺点
优点 | 缺点 |
---|---|
检测时间仍然很好:完全停机需要2分10秒(36600.1%, 36:小时;60:分钟;0.1%:上文所计算得到的10分钟的平均值) | 非常差的恢复时间:在100%停机的情况下,报警将在2分钟后触发,并在接下来的36小时内持续 |
比前一个示例更精确:通过确保错误率持续更长时间,报警可能会对错误预算构成重大威胁 | 由于存在大量数据点,因此在较长窗口上计算速率在存储器或I/O操作方面可能代价较大 |
图5-2显示,虽然在36小时内,错误率已降至可忽略不计的水平,但36小时的平均错误率仍高于阈值。
3. 增加报警持续时间
大多数监控系统允许你将持续时间参数添加到报警规则,因此报警不会被触发,除非该值在一段时间内保持在阈值之上。你可能想使用此参数作为低成本方式增加更长的窗口:
1 |
|
表5-3显示了使用持续时间参数进行报警的优缺点。
优点 | 缺点 |
---|---|
报警可以更高精度。在触发之前需要持续的错误率意味着报警更可能对应于重大事件。 | 召回率和检测时间不佳:由于持续时间不随事件严重程度而变化,因此在100%服务中断一小时后才会发出报警,0.2%服务中断也会有相同的检测时间。100%的中断将消耗30天预算的140%。即使度量标准暂时返回到SLO内的级别,持续时间计时器也将重置。 当SLI在满足于不满足SLO之间波动时可能永远不会发出报警。 |
由于表5-3中列出的原因,我们不建议将持续时间用作基于SLO的报警标准的一部分
图5-3显示了在报警触发前持续10分钟的服务窗口内5分钟内的平均错误率。每隔10分钟出现的持续5分钟的错误高峰永远不会触发报警,但是总体上看出错率是35%。
每个峰值消耗了30天预算的近12%,但报警从未触发。
4. 关于消耗率的报警
要改进以前的解决方案,你需要创建具有良好检测时间和高精度的报警规则。为此, 你可以引入消耗速率以减小窗口大小,同时保持报警预算花费不变。
消耗速率是指相对于SLO,服务消耗错误预算的速度。 图5-4显示了消耗率和错误预算之间的关系。
示例服务使用了100%消耗率,这意味着它正在消耗错误预算,其速率使您在SLO的时间窗口结束时只剩下0的错误预(请参阅第一本书中的第4章)。 在30天的时间窗口内SLO为99.9%,持续的0.1%错误率正好可以在一个月内消耗完所有错误预算:消耗率为100%。
表5-4显示了消耗速率,相应的错误率以及耗尽SLO预算所需的时间。
Burn rate | Error rate for a 99.9% SLO | Time to exhaustion |
---|---|---|
1 | 0.1% | 30days |
2 | 0.2% | 15days |
10 | 1% | 3days |
1000 | 100% | 43minutes |
通过将报警窗口定为一小时,并设定当消耗掉当月5%的错误预算时发出告警,你可以得到用于报警的消耗率阈值。对于基于消耗率的报警,报警触发所需的时间为:
1 |
|
报警触发时消耗的错误预算为:
1 |
|
1小时的告警窗口消耗掉30天错误预算的5%时,错误预算的消耗率为36。报警规则现在变为:
1 |
|
表5-5 显示了基于消耗率的报警的优缺点。
优点 | 缺点 |
---|---|
良好的精确度:此策略选择大部分错误预算支出以提醒发出报警。更短的时间窗口,计算起来代价较小。 检测时间好。更好的恢复时间:58分钟。 | 低召回率:35%(与上下文的36相对)的消耗率永远不会发出报警,但会在20.5小时内消耗掉所有30天的误差预算。重置时间:58分钟仍然太长 |
5. 多次消耗率报警
你的报警逻辑可以使用多个消耗速率和时间窗口,并在消耗速率超过指定阈值时触发报警。 此选项保留了消耗率报警的好处,并确保你不会忽略较低(但仍然很重要)的错误率。
为事件设置工单通知也是一个好主意,这些事件通常会被忽视,但如果不加以控制可能会耗尽你的错误预算 - 例如,三天内预算消耗率为10%。 这种错误率可以捕获重大事件,但由于预算消耗率提供了足够的时间来处理事件,因此你无需紧急通知某人。
我们建议在一小时内将2%的预算消耗和6小时内的5%预算消耗作为紧急通知是合理起始数量,并在三天内将10%预算消耗作为故障工单报警的良好基准。适当的数字取决于服务和基本的报警负载。对于更繁忙的服务,并且根据周末和假日的待命责任oncall, 可能需要六小时窗口的工单提醒。
表5-6显示了消耗的SLO预算百分比的相应消耗率和时间窗口。
SLO budget consumption | Time window | Burn rate | Notification |
---|---|---|---|
2% | 1hour | 14.4 | Page |
5% | 6hours | 6 | Page |
10% | 3day | 1 | Ticket |
报警配置可能类似于如下规则:
1 |
|
图5-5显示了根据错误率的检测时间和报警类型。
多个消耗速率允许你根据响应速度调整报警以提供适当的优先级。如果问题在几小时或几天内耗尽错误预算,则发送有效通知是合适的。否则,在下一个工作日处理基于工单的报警通知则更合适。表5-7列出了使用多种消耗率的优缺点。
优点 | 缺点 |
---|---|
能够根据关键值调整监控配置以适应多种情况:错误率高时快速报警;如果错误率很低但持续,最终会发出报警。良好的精度,与所有固定预算的部分报警方法一样。 因为是三天的时间窗口,所以有很好的召回率。能够根据人们对防御SLO的反应速度来选择最合适的报警类型 | 更多数据、窗口大小和阈值需要管理和推理。 由于三天的窗口,更长的恢复时间。 如果所有条件均为真,则要避免触发多个报警,你需要实施报警屏蔽。 例如:5分钟内10%的预算支出也意味着5%的预算在6小时内消耗完,2%的预算消耗在1小时之内。此方案将触发三个通知,除非监控系统足够智能以防止它这样做 |
6. 多窗口,多消耗率报警
我们可以在第五节中增强多消耗率报警,以便仅在我们仍在快速消耗预算时通知我们 - 从而减少误报的数量。 为此,我们需要添加另一个参数:一个较短的窗口,用于检查在触发报警时是否仍在消耗错误预算。
一个好的方案是将短窗口设为长窗口持续时间的1/12,如图5-6所示。 该图显示了报警阈值。 在经历了10分钟的15%错误之后,短窗口平均值立即超过报警阈值,并且在5分钟后长窗口平均值超过阈值,此时报警开始触发。 错误停止后5分钟,短窗口平均值降至阈值以下,此时报警停止触发。 错误停止后60分钟,长窗口平均值降至阈值以下。
例如,你可以在前一小时和前五分钟超过14.4倍消耗率时发送工单级报警。 只有在消耗了2%的预算后,此报警才会触发,但通过在五分钟后停止发送而不是一小时后显示更好的恢复时间:
我们建议将表5-8中列出的参数作为基于SLO的报警配置的起点。
Serverity | Long window | Short window | Butn rate | budget consumption |
---|---|---|---|---|
Page | 1hour | 5minutes | 14.4 | 2% |
Page | 6hours | 30minutes | 6 | 5% |
Ticket | 3day | 6hour | 1 | 10% |
我们发现基于了多消耗率的报警是实现基于SLO的报警的有效方式。表5-9显示了使用多种消耗率和窗口大小的优点和缺点。
优点 | 缺点 |
---|---|
灵活的报警框架,允许你根据事件的严重性和组织的要求控制报警类型 要指定的参数很多,这可能使报警规则难以管理 | 良好的精度,与所有固定预算的部分报警方法一样。不错的召回率,因为有三天的窗口 有关管理报警规则的更多信息,请参阅第89页的“按比例报警” |
低流量服务和错误预算报警
当出现问题需要提供有意义的信息且请求率较高时,详细说明的多窗口、多点消耗方法很有效。但是,这些方法可能会导致接收请求率较低的系统出现问题。如果系统具有较少的用户数或自然的低流量时段(例如夜晚和周末),则可能需要更改你的方法。
在低流量服务中自动区分不重要事件更加困难。 例如,如果系统每小时收到10个请求,则单个失败的请求会导致每小时错误率为10%。 对于99.9%的SLO,此请求构成1,000x消耗率并立即发出报警,因为它消耗了30天误差预算的13.9%。 此方案在30天内仅允许七个失败的请求。 单个请求可能会因大量短暂且令人厌倦的原因而失败,这些原因与大型系统中断一样,不一定能用成本效益的方式解决。
最佳解决方案取决于服务的性质:单个请求失败的影响是什么? 如果失败的请求是一次性的、高价值的、没有重试的请求,那么高可用性目标可能是合适的。从业务角度来看,调查每个失败的请求都是有意义的。但是,在这种情况下,报警系统会延迟通知错误。我们建议使用几个关键选项来处理低流量服务:
- 人工生成流量以补偿来自真实用户的信号不足。
- 将较小的服务组合成更大的服务以用于监控目的。
- 修改产品,以便:
- – 需要更多请求才能将单个事件限定为失败。
- – 单一故障的影响较小。
人工生成流量
系统可以模拟用户活动以检查潜在错误和高延迟请求。在没有真实用户的情况下,你的监控系统可以检测到模拟错误和请求,因此你的值班工程师可以在影响太多实际用户之前对问题做出响应。
人工流量提供更多信号,并允许你重用现有的监控逻辑和SLO值。你甚至可能已经拥有大部分必要的流量生成组件,例如黑盒探测器和集成测试。
生成人工负载确实有一些缺点。大多数需要SRE支持的服务都很复杂,而且系统控制面很大。理想情况下,系统应进行设计和更改,以便使用人工流量进行监控。 即使是非常重要的服务,你也只能合成用户请求类型总数的一小部分。 对于有状态的服务,更多的状态会加剧这个问题。
此外,如果问题影响真实用户但不影响人工流量,则成功的人工请求会隐藏真实的用户信号,因此你不会收到用户看到的错误通知。
合并服务
如果多个低流量服务对一个整体功能有贡献,则将它们的请求组合到单个更高级别的组中可以更精确地检测重要事件并且具有更少的误报。 要使这种方法起作用,服务必须以某种方式相关联 ——你可以组合构成同一产品的一部分的微服务,或者由同一个二进制文件处理的多个请求类型。
组合服务的缺点是单个服务的完全失败可能不算是重大事件。 通过选择具有共享故障域的服务(例如公共后端数据库),可以增加故障影响整个组的可能性。 你仍然可以使用较长时间的报警,最终可以100%的捕获单个服务故障。
进行服务和基础设施更改
对重大事件发出报警旨在提供足够的通知,以便在耗尽整个错误预算之前缓解问题。 如果你无法将监控调整为对短暂事件不太敏感,并且生成人工流量不切实际,则可以考虑更改服务以减少单个失败请求对用户的影响。 例如,你可能:
- 修改客户端以使用指数退避和抖动进行重试。
- 设置捕获最终执行请求的回退路径,这可以在服务器或客户端上进行。
这些更改对于高流量系统非常有用,但对于低流量系统更是如此:它们允许在错误预算中有更多的失败事件,更多的普通信号,以及更多的时间在事件变得重要之前对其做出反应。
降低SLO或增加窗口
你可能还想重新考虑单个故障对错误预算的影响是否准确反映了其对用户的影响。 如果少量错误导致你丢失错误预算,你是否真的需要寻找工程师来立即解决问题? 如果没有,用户会对较低的SLO同样满意。 通过较低的SLO,工程师只会收到更大的持续中断报警通知。
一旦你与服务的利益相关者协商降低SLO(例如,将SLO从99.9%降低到99%),实施更改非常简单:如果你已经有系统用于报告,监控和报警,则基于 SLO阈值,只需将新SLO值添加到相关系统即可。
降低SLO确实有缺点:它涉及产品决策。 更改SLO会影响系统的其他方面,例如对系统行为的期望以及何时制定错误预算策略。 这些其他要求对于产品而言可能比避免一些低信号报警更重要。以类似的方式,增加用于报警逻辑的时间窗口确保触发页面的报警更加重要并且值得关注。在实践中,我们使用以下方法的某种组合来警告低流量服务:
- 在这样做时产生虚假流量是可能的并且可以实现良好的覆盖
- 修改客户端,以便短暂的故障不太可能导致用户影响
- 聚合共享某种故障模式的较小服务
- 设置SLO阈值与失败请求的实际影响相对应
极端可用性目标
具有极低或极高可用性目标的服务可能需要特别考虑。 例如,考虑具有90%可用性目标的服务。 表5-8表示了当在一个小时内消耗了2%的错误预算时的报警。因为100%的宕机只会在那个小时消耗掉1.4%的预算,所以这个报警永远不会触发。如果你的错误预算是在很长一段时间内设置的,那么你可能需要调整报警参数。
对于具有极高可用性目标的服务,100%中断的耗尽时间非常短。 对于每月目标可用性为99.999%的服务,100%的中断将在26秒内耗尽其预算——这比许多监控服务的采集周期小很多,更不用说生成报警时通过电子邮件和短信等通知系统传递它的目的端时间了。 即使报警直接发送到自动解决方案系统,问题也可能完全消耗错误预算,然后才能得到缓解它。
收到通知说你只剩下26秒的预算并不一定是一个坏策略;这对于保护SLO是没有用的。 防御这种可靠性的唯一方法是设计系统,使100%中断的可能性极低。 这样,你可以在消耗预算之前解决问题。 例如,如果你最初将此更改推广到仅有1%的用户,并以1%的相同速率消耗错误预算,那么现在你要43分钟才能耗尽错误预算。 有关设计此类系统的策略,请参阅第16章。
大规模报警
在扩展服务时,请确保报警同样可扩展。 你可能想为各个服务指定自定义报警参数。 如果你的服务包含100个微服务(或等效地,具有100种不同请求类型的单个服务),这种情况很快就会积累起无法衡量的工作和认知负载。
在这种情况下,我们强烈建议不要为每项服务单独指定报警窗口和消耗率参数,因为这样做很快就会变得势不可挡。确定报警参数后,将它们应用于所有服务。
管理大量SLO的一种技术是将请求类型分组到大致类似的可用性要求的桶中。 例如,对于具有可用性和延迟SLO的服务,可以将其请求类型分组到以下存储桶中:
CRITICAL
对于最重要的请求类型,例如用户登录服务时的请求。
HIGH_FAST
适用于具有高可用性和低延迟要求的请求。 这些请求涉及核心交互功能,例如当用户点击按钮以查看他们的广告库存本月赚了多少钱。
HIGH_SLOW
对于重要但对延迟不太敏感的请求,比如用户单击按钮生成过去几年所有广告活动的报告,并且不希望数据立即返回。
LOW
对于必须具有某些可用性,但是对于用户来说几乎不可见的中断的请求 —— 例如,轮询处理程序以查看可能长时间失败而不会对用户产生影响的帐户通知。
NO_SLO
对于用户完全不可见的功能 ——例如,暗启动或显式位于任何SLO之外的alpha功能。
通过对请求进行分组而不是在所有请求类型上放置唯一可用性和延迟目标,可以将请求分组到五个存储桶中,如表5-10中的示例所示。
Request class | Availability | Latency @ 90% | Latency@99% |
---|---|---|---|
CRITICAL | 99.99% | 100 ms | 200 ms |
HIGH_Fast | 99.9% | 100 ms | 200 ms |
HIGH_SLOW | 99.9% | 1000 ms | 5000 ms |
LOW | 99% | None | None |
NO_SLO | None | None | None |
这些存储桶提供了足够的保真度来保护用户的满意度,但与一个更复杂、管理成本更高的系统相比,它的工作量更小,而且可能更精确地反映用户体验。
结论
如果你设置的SLOs是有意义的、可理解的,并且可度量,那么你可以配置报警,只有在错误预算中存在可操作的、特定的威胁时才通知值班人员。
用于警告重大事件的技术包括从错误率高于SLO阈值时发出报警,到使用多级消耗率和窗口大小。 在大多数情况下,我们认为多窗口、多消耗率报警技术是保护应用程序SLO的最佳方法。
我们希望我们提供了为你自己的应用程序和组织做出正确配置决策时所需的环境和工具。