본문으로 건너뛰기
Kreath Archive
TechProjectsBooksAbout
TechProjectsBooksAbout

내비게이션

  • Tech
  • Projects
  • Books
  • About
  • Tags

카테고리

  • AI / ML
  • 웹 개발
  • 프로그래밍
  • 개발 도구

연결

  • GitHub
  • Email
  • RSS
© 2026 Kreath Archive. All rights reserved.Built with Next.js + MDX
홈TechProjectsBooksAbout
//
  1. 홈
  2. 테크
  3. 10장: SLO 기반 알림 설계
2026년 2월 26일·인프라·

10장: SLO 기반 알림 설계

SLI/SLO/에러 버짓의 개념을 정립하고, 번 레이트 알림(fast-burn/slow-burn), Prometheus 알림 규칙, Grafana 알림 채널을 설계합니다.

15분687자8개 섹션
monitoringobservability
공유
opentelemetry10 / 11
1234567891011
이전9장: AI 서비스 관측 가능성다음11장: 실전 프로젝트 -- 관측 가능성 플랫폼 구축

학습 목표

  • SLI, SLO, 에러 버짓의 개념과 관계를 정립합니다
  • 번 레이트(Burn Rate) 알림의 원리를 이해합니다
  • 다중 윈도우 알림 전략(fast-burn/slow-burn)을 설계합니다
  • Prometheus 알림 규칙을 작성하고 Grafana로 시각화합니다
  • PagerDuty, Slack 통합 알림 채널을 구성합니다

SLI, SLO, 에러 버짓

SLI — 서비스 수준 지표

**SLI(Service Level Indicator)**는 서비스 품질을 정량적으로 측정하는 지표입니다. 주로 비율(ratio)로 표현하며, 0에서 1(또는 0%에서 100%) 사이의 값을 가집니다.

SLI 유형정의측정 방법
가용성(Availability)성공한 요청 / 전체 요청HTTP 2xx-4xx / 전체 응답
지연 시간(Latency)임계값 이내 요청 / 전체 요청300ms 이내 응답 비율
처리량(Throughput)처리된 작업 / 예상 작업완료된 배치 / 전체 배치
정확성(Correctness)올바른 응답 / 전체 응답유효한 결과 비율

SLO — 서비스 수준 목표

**SLO(Service Level Objective)**는 SLI의 목표 임계값입니다. "이 정도의 품질은 반드시 유지해야 한다"는 약속입니다.

text
SLO 예시:
- 가용성: 월간 99.9% (한 달에 43분의 다운타임 허용)
- 지연 시간: p99 응답 시간 500ms 이내, 월간 99.5%
- AI 서비스: LLM 응답 시간 5초 이내, 월간 99.0%
Tip

SLO는 100%를 목표로 하지 않습니다. 100%는 사실상 불가능하며, 과도하게 높은 SLO는 배포 속도를 저하시킵니다. 사용자 경험과 개발 속도 사이의 균형점을 찾는 것이 SLO 설계의 핵심입니다.

에러 버짓 — 실패의 허용량

**에러 버짓(Error Budget)**은 SLO에서 허용하는 실패의 총량입니다. 99.9% 가용성 SLO는 0.1%의 에러 버짓을 의미합니다.

text
30일 기준 에러 버짓 계산:
- 99.9% SLO → 0.1% 에러 버짓 → 30일 x 24시간 x 60분 x 0.001 = 43.2분
- 99.5% SLO → 0.5% 에러 버짓 → 30일 x 24시간 x 60분 x 0.005 = 216분 (3.6시간)
- 99.0% SLO → 1.0% 에러 버짓 → 30일 x 24시간 x 60분 x 0.01 = 432분 (7.2시간)

에러 버짓이 남아 있으면 새로운 기능 배포나 실험을 진행할 수 있고, 에러 버짓이 소진되면 안정성 개선에 집중해야 합니다. 이것이 에러 버짓 정책(Error Budget Policy)입니다.


SLI를 OTel 메트릭으로 정의하기

OpenTelemetry 메트릭을 SLI 측정에 활용합니다.

가용성 SLI

sli_availability.py
python
from opentelemetry import metrics
 
meter = metrics.get_meter("sli-service")
 
# 전체 요청 수 (성공 + 실패)
request_total = meter.create_counter(
    "sli.request.total",
    description="Total number of requests for SLI calculation",
)
 
# 성공 요청 수 (SLI 기준의 "좋은" 이벤트)
request_good = meter.create_counter(
    "sli.request.good",
    description="Number of good requests (non-5xx)",
)
 
def record_request(status_code: int, method: str, endpoint: str):
    attrs = {"http.method": method, "sli.endpoint": endpoint}
    request_total.add(1, attrs)
    
    # 5xx가 아닌 응답은 "좋은" 요청으로 간주
    if status_code < 500:
        request_good.add(1, attrs)

지연 시간 SLI

sli_latency.py
python
# 응답 시간 히스토그램 -- SLO 임계값에 맞는 버킷 설정
request_duration = meter.create_histogram(
    "sli.request.duration",
    description="Request duration for latency SLI",
    unit="s",
)
 
# 사용 시 PromQL로 SLI 계산:
# sum(rate(sli_request_duration_seconds_bucket{le="0.3"}[5m]))
# / sum(rate(sli_request_duration_seconds_count[5m]))

PromQL로 SLI 계산

SLI PromQL 쿼리
promql
# 가용성 SLI (30일 윈도우)
sum(rate(sli_request_good_total[30d]))
/ sum(rate(sli_request_total_total[30d]))
 
# 지연 시간 SLI (p99가 300ms 이내인 비율)
sum(rate(sli_request_duration_seconds_bucket{le="0.3"}[30d]))
/ sum(rate(sli_request_duration_seconds_count[30d]))
 
# 에러 버짓 잔량 (%)
1 - (
  (1 - (sum(rate(sli_request_good_total[30d])) / sum(rate(sli_request_total_total[30d]))))
  / (1 - 0.999)
)

번 레이트 알림

기존 알림의 문제점

단순 임계값 알림(에러율이 0.1%를 초과하면 알림)에는 심각한 문제가 있습니다.

  • 잦은 오탐 — 순간적 에러 스파이크에도 알림 발생
  • 느린 감지 — 완만한 품질 저하를 놓침
  • 컨텍스트 부족 — 에러 버짓 소진 속도를 알 수 없음

번 레이트란

**번 레이트(Burn Rate)**는 에러 버짓이 소진되는 속도입니다. 번 레이트 1은 정확히 SLO 기간(보통 30일) 동안 에러 버짓을 소진하는 속도를 의미합니다.

번 레이트의미에러 버짓 소진 시간 (30일 SLO)
1x정상 속도30일
2x2배 빠른 소진15일
10x10배 빠른 소진3일
14.4x24시간 소진~1일
720x1시간 소진1시간

다중 윈도우 번 레이트 알림

Google SRE 책에서 권장하는 다중 윈도우(Multi-Window) 전략은 두 가지 윈도우로 구성됩니다.

Fast Burn (빠른 소진): 급격한 장애 감지

  • 1시간 윈도우에서 번 레이트 14.4x 이상
  • 5분 윈도우에서도 동일 조건 확인 (짧은 윈도우로 오탐 방지)
  • 즉각 대응이 필요한 Critical 알림

Slow Burn (느린 소진): 완만한 품질 저하 감지

  • 6시간 윈도우에서 번 레이트 6x 이상
  • 30분 윈도우에서도 동일 조건 확인
  • 조사가 필요한 Warning 알림

Prometheus 알림 규칙

가용성 SLO 알림

slo-alert-rules.yaml
yaml
groups:
  - name: slo-availability
    rules:
      # 에러율 계산을 위한 기록 규칙
      - record: sli:error_rate:1h
        expr: |
          1 - (
            sum(rate(sli_request_good_total[1h]))
            / sum(rate(sli_request_total_total[1h]))
          )
 
      - record: sli:error_rate:5m
        expr: |
          1 - (
            sum(rate(sli_request_good_total[5m]))
            / sum(rate(sli_request_total_total[5m]))
          )
 
      - record: sli:error_rate:6h
        expr: |
          1 - (
            sum(rate(sli_request_good_total[6h]))
            / sum(rate(sli_request_total_total[6h]))
          )
 
      - record: sli:error_rate:30m
        expr: |
          1 - (
            sum(rate(sli_request_good_total[30m]))
            / sum(rate(sli_request_total_total[30m]))
          )
 
      # Fast Burn 알림 (99.9% SLO, 에러 버짓 = 0.001)
      - alert: SLO_HighErrorRate_FastBurn
        expr: |
          sli:error_rate:1h > (14.4 * 0.001)
          and
          sli:error_rate:5m > (14.4 * 0.001)
        for: 2m
        labels:
          severity: critical
          slo: availability
        annotations:
          summary: "가용성 SLO 위반 위험 - 빠른 에러 버짓 소진"
          description: >
            1시간 에러율이 SLO 허용 범위의 14.4배를 초과하고 있습니다.
            이 속도로는 약 1일 내에 월간 에러 버짓이 소진됩니다.
          dashboard: "https://grafana.example.com/d/slo-dashboard"
 
      # Slow Burn 알림
      - alert: SLO_HighErrorRate_SlowBurn
        expr: |
          sli:error_rate:6h > (6 * 0.001)
          and
          sli:error_rate:30m > (6 * 0.001)
        for: 5m
        labels:
          severity: warning
          slo: availability
        annotations:
          summary: "가용성 SLO 서서히 저하 - 느린 에러 버짓 소진"
          description: >
            6시간 에러율이 SLO 허용 범위의 6배를 초과하고 있습니다.
            이 속도로는 약 5일 내에 월간 에러 버짓이 소진됩니다.

지연 시간 SLO 알림

slo-latency-rules.yaml
yaml
groups:
  - name: slo-latency
    rules:
      # p99 지연 시간 SLI 기록 규칙
      - record: sli:latency_good_rate:1h
        expr: |
          sum(rate(sli_request_duration_seconds_bucket{le="0.3"}[1h]))
          / sum(rate(sli_request_duration_seconds_count[1h]))
 
      - record: sli:latency_good_rate:5m
        expr: |
          sum(rate(sli_request_duration_seconds_bucket{le="0.3"}[5m]))
          / sum(rate(sli_request_duration_seconds_count[5m]))
 
      # Fast Burn -- 지연 시간 SLO (99.5%, 에러 버짓 = 0.005)
      - alert: SLO_HighLatency_FastBurn
        expr: |
          (1 - sli:latency_good_rate:1h) > (14.4 * 0.005)
          and
          (1 - sli:latency_good_rate:5m) > (14.4 * 0.005)
        for: 2m
        labels:
          severity: critical
          slo: latency
        annotations:
          summary: "지연 시간 SLO 위반 위험"
          description: >
            300ms 이내 응답 비율이 급격히 하락하고 있습니다.

Grafana SLO 대시보드

SLO 상태 패널 구성

SLO 대시보드 쿼리
promql
# 현재 가용성 SLI (30일 윈도우)
sum(rate(sli_request_good_total[30d]))
/ sum(rate(sli_request_total_total[30d]))
 
# 에러 버짓 잔량 (%)
(
  1 - (
    (1 - sum(rate(sli_request_good_total[30d])) / sum(rate(sli_request_total_total[30d])))
    / 0.001
  )
) * 100
 
# 에러 버짓 소진 추이 (시간별)
1 - (
  sum(increase(sli_request_good_total[1h]))
  / sum(increase(sli_request_total_total[1h]))
) / 0.001

대시보드 레이아웃

행패널설명
1SLO 상태 게이지 (가용성, 지연시간)현재 SLI 값과 SLO 목표
2에러 버짓 잔량 게이지남은 에러 버짓 비율
3에러 버짓 소진 추이 그래프시간별 소진 속도
4번 레이트 현황현재 번 레이트와 임계값
5SLO 위반 이력알림 발생 이력 타임라인

알림 채널 구성

Grafana 알림 라우팅

grafana-alerting.yaml
yaml
apiVersion: 1
contactPoints:
  - name: critical-channel
    receivers:
      - uid: pagerduty-critical
        type: pagerduty
        settings:
          integrationKey: "$PAGERDUTY_KEY"
          severity: critical
      - uid: slack-incidents
        type: slack
        settings:
          url: "$SLACK_WEBHOOK_URL"
          channel: "#incidents"
          title: "SLO Critical Alert"
 
  - name: warning-channel
    receivers:
      - uid: slack-warnings
        type: slack
        settings:
          url: "$SLACK_WEBHOOK_URL"
          channel: "#slo-warnings"
 
policies:
  - receiver: critical-channel
    matchers:
      - severity = critical
    continue: false
    
  - receiver: warning-channel
    matchers:
      - severity = warning
    group_wait: 5m
    repeat_interval: 1h

알림 라우팅 전략

Info

알림 피로(Alert Fatigue)를 방지하는 것이 핵심입니다. Fast Burn 알림만 온콜 엔지니어에게 PagerDuty로 전송하고, Slow Burn 알림은 Slack 채널로 전달하여 업무 시간에 확인하도록 합니다. 모든 알림을 Critical로 설정하면 정작 중요한 알림을 놓치게 됩니다.

알림 유형심각도채널대응
Fast Burn (14.4x)CriticalPagerDuty + Slack즉각 대응 (5분 내)
Slow Burn (6x)WarningSlack업무 시간 내 조사
에러 버짓 75% 소진InfoSlack주간 리뷰에서 논의
에러 버짓 100% 소진CriticalPagerDuty + Slack배포 동결 + 안정성 집중

정리

이번 장에서는 SLI/SLO/에러 버짓의 개념과 관계를 정립하고, 번 레이트 기반의 지능형 알림 전략을 설계했습니다. 다중 윈도우 번 레이트 알림은 급격한 장애(Fast Burn)와 완만한 품질 저하(Slow Burn)를 모두 감지할 수 있으며, Prometheus 기록 규칙과 알림 규칙으로 구현했습니다. Grafana SLO 대시보드와 PagerDuty/Slack 알림 채널 구성도 실습했습니다.

다음 장에서는 이 시리즈의 마지막으로, 전체 관측 가능성 플랫폼을 실전 프로젝트로 구축합니다. 마이크로서비스 계측, AI 서비스 관측, SLO 알림, 운영 체크리스트, 비용 최적화를 종합적으로 다룹니다.

이 글이 도움이 되셨나요?

관련 주제 더 보기

#monitoring#observability

관련 글

인프라

11장: 실전 프로젝트 -- 관측 가능성 플랫폼 구축

마이크로서비스 계측, AI 서비스 관측, SLO 알림을 종합하여 전체 관측 가능성 플랫폼을 구축하고, 운영 체크리스트와 비용 최적화 전략을 정리합니다.

2026년 2월 28일·14분
인프라

9장: AI 서비스 관측 가능성

LLM 호출 추적, 토큰 사용량/비용 모니터링, AI 에이전트 행동 추적, LangChain/LlamaIndex OTel 통합을 통한 AI 관측 가능성을 학습합니다.

2026년 2월 24일·12분
인프라

8장: Grafana, Jaeger, Prometheus 연동

Jaeger로 분산 추적을 시각화하고, Prometheus로 메트릭을 저장/쿼리하며, Grafana로 통합 대시보드를 구성합니다. Docker Compose로 전체 스택을 실습합니다.

2026년 2월 22일·12분
이전 글9장: AI 서비스 관측 가능성
다음 글11장: 실전 프로젝트 -- 관측 가능성 플랫폼 구축

댓글

목차

약 15분 남음
  • 학습 목표
  • SLI, SLO, 에러 버짓
    • SLI — 서비스 수준 지표
    • SLO — 서비스 수준 목표
    • 에러 버짓 — 실패의 허용량
  • SLI를 OTel 메트릭으로 정의하기
    • 가용성 SLI
    • 지연 시간 SLI
    • PromQL로 SLI 계산
  • 번 레이트 알림
    • 기존 알림의 문제점
    • 번 레이트란
    • 다중 윈도우 번 레이트 알림
  • Prometheus 알림 규칙
    • 가용성 SLO 알림
    • 지연 시간 SLO 알림
  • Grafana SLO 대시보드
    • SLO 상태 패널 구성
    • 대시보드 레이아웃
  • 알림 채널 구성
    • Grafana 알림 라우팅
    • 알림 라우팅 전략
  • 정리