Error budgets concept diagram. Production service (api-1, api-2, api-3, Prometheus, Alertmanager) feeds burn-rate signals into release controls (feature-flag-svc, deploy-pipeline, on-call). Three scenarios: monthly budget tracking with healthy state allowing free deploys, fast burn alert (14.4x burn rate, multi-window) paging on-call after a bad deploy, and budget-exhausted state automatically freezing deploys via feature-flag service with override path. Two ADRs embedded: (1) multi-window multi-burn-rate alert design, (2) budget-exhausted response policy: hard freeze default with VP-Eng override.
Error budget превращает абстрактную «надёжность» в конкретную валюту: сколько минут downtime или неуспешных запросов команда может потратить на эксперименты, рискованные deploy и миграции. Это разрешает вечный конфликт product («ship fast») vs SRE («don't break»): если бюджет есть — рискуем; если кончился — замораживаемся. Решение принимает не голос самого громкого в комнате, а математика.
Главное переосмысление: reliability — это product trade-off, а не «as much as possible». 100% надёжности не нужно никому (и физически недостижимо), зато выделенный бюджет даёт команде свободу инноваций без споров на вкус.
Формула одна:
error_budget = 1 - SLO
Для SLO 99.9% за 30 дней — это 0.1% × 30 × 24 × 60 ≈ 43 минуты downtime или 10 000 ошибок на каждые 10M запросов. Если за первую неделю инцидент сжёг 30 минут — на оставшиеся 3 недели осталось 13. Любой рискованный deploy теперь требует обоснования, а не «по дефолту».
Но сама формула без policy — бессмыслица. Policy — это заранее согласованный документ что происходит в каждом состоянии бюджета:
| Состояние | Действие |
|---|---|
| Healthy (>50%) | Ship freely, эксперименты, deploy в пятницу OK |
| At risk (10-50%) | Code review строже, no Friday deploys, canary >1h |
| Exhausted (<10%) | Freeze new features, only reliability fixes |
| Violated (<0%) | SLO review, retro, возможен запрос на reliability hiring |
Document должен подписать VP Engineering — иначе при первом freeze начнётся торговля. Google в SRE Book Ch.3 называет policy контрактом между product и SRE.
Две группы:
ADR-001: multi-window multi-burn-rate alerts).ADR-002: hard freeze vs override), Deploy pipeline, и On-call SRE.Клиенты слева: Developer толкает код в pipeline, Users (10M req/мес) генерируют метрики. Связи: метрики идут api → prom, бюджет-сигнал prom → alertmanager → feature-flag, а deploy pipeline проходит pre-deploy gate через feature-flag (он же блокирует деплои при freeze).
Steady-state: burn rate стабильно ниже 1×, бюджет 87%. Когда developer пушит рискованную миграцию, deploy pipeline спрашивает feature-flag service «можно?», получает [OK] healthy -> ship freely, и канарейка едет 5% → 100%. Alertmanager шлёт only weekly digest, никаких пейджей. Это то состояние, ради которого вообще существует концепция бюджета — разрешение рисковать.
Кто-то выкатил v2.4.0 без canary, новая retry-логика забагована, 30% запросов падают в 500. Multi-window alert ловит это за минуты: и 1h-окно, и 5m-окно показывают burn rate 14.4× — пейджер звонит SEV-2 с текстом «Will exhaust 30d budget in 5h». On-call откатывает за 12 минут, burn возвращается к 0.9×. Без multi-window наивный alert ждал бы 24 часа усреднения и приехал бы после катастрофы; с одним коротким окном — флэпал бы от каждого минутного спайка.
Кумулятивно накопленные мелкие инциденты опустили бюджет до 8%. Alertmanager переводит feature-flag в состояние EXHAUSTED, и pipeline автоматически блокирует следующий feature-deploy (новый дашборд) с сообщением [BLOCKED] budget < 10%, feature deploys frozen. Reliability fix с тегом risk:exempt проходит через тот же gate без сопротивления — freeze не значит «вообще ничего», freeze значит «только то, что чинит, а не добавляет риск».
ADR-001: Multi-window multi-burn-rate vs single-window alerts. Наивный «pager когда budget = 0» приходит после outage. Single-window либо шумит (1h флэпает), либо опаздывает (24h усреднение пропустит fast burn). SRE Workbook Ch.5 рекомендует пары окон: короткое детектирует, длинное подтверждает. Калибровка из таблицы: 14.4× over (1h, 5m) → page; 6× over (6h, 30m) → ticket; 3× over (24h, 2h) → dashboard. SoundCloud в 2019 опубликовал post: pages упали на 60% после миграции на эту схему.
ADR-002: Hard freeze vs override. Когда бюджет кончается — что делать с security CVE, который ширится как feature flag? С regulator-mandated change? Жёсткий freeze теряет business value; лёгкий override превращает policy в театр («freeze fatigue» по HashiCorp). Решение: freeze это default и не требует апрува (pipeline auto-blocks). Override требует (a) обоснования в PR, (b) подписи VP Eng + on-call SRE, (c) armed auto-rollback при дополнительном burn 50%. Security CVE и compliance changes — pre-approved exceptions с тегом risk:exempt. Количество override само становится SLI: >2 за квартал → пересмотр SLO (возможно, он слишком тугой).
Per-service vs per-CUJ budget. Альтернатива — считать бюджет на сервис (Postgres availability), а не на critical user journey (checkout success). Per-service проще операционно, but per-CUJ ближе к бизнесу. Хорошо иметь оба: сервис может быть «технически 99.99%», а CUJ — 99.5% из-за совокупности зависимостей. Бюджет владельца — CUJ, attribution делится по вкладу зависимостей в инциденты.
Инструменты: Sloth (YAML → Prometheus rules, free), Pyrra (K8s CRDs, free), OpenSLO (vendor-neutral spec), Grafana SLO / Datadog SLO / Honeycomb SLO / Nobl9 (managed, $$).
Концепция error budget предполагает что у тебя есть измеримый SLI (success rate, latency p99) и окно достаточной длины чтобы статистика была значимой. Не работает когда:
Связанные концепты: [CONCEPT]sli-slo-sla — формальные определения SLI/SLO/SLA; [CONCEPT]incident-management — как организовать ответ на page; [CONCEPT]post-mortems — что делать после того как бюджет был сожжён.