はじめに
ゼロバンク・デザインファクトリー株式会社(ZDF)で、みんなの銀行におけるBaaSサービスのインフラ基盤の構築・運用を担当している斉木です。
みんなの銀行、BaaSサービスについては、以下をご覧ください。
SLI/SLO 運用について
今回は、BaaSサービスのインフラ基盤チームで実践しているSREプラクティスのうち、SLI/SLOの取り組みについて取り上げさせていただきます。
SLI/SLOの定義はSREの基本ですが、導入や運用に課題を抱えている企業も多いかと思います。設定したSLOを目指した運用・改善には、新機能構築以外の継続的な開発体制の確保が必要です。
成長期の企業や運用作業が肥大化した環境では、導入に向けたリソース確保に一定のハードルを感じます。運用における手動作業や定型作業(SREで言うトイル)が自動化され、継続的に解消され続ける文化・体制が重要です。
我々のチームでも同様の課題感を持ちつつ、新規構築・運用作業・トイルの削減を進める傍ら、SLI/SLOの導入に向けたPoCを進めておりました。
SLI/SLOは機能開発や改善が活発な環境では、一度設定しても継続的に更新が必要になります。GUI上で手動設定すると変更作業が煩雑になり、CI/CDの恩恵も受けられず、要件の更新速度に追従する際の足枷になります。
また、変更履歴が残らず、環境間の差異も生まれがちです。そこで私たちは、SLI/SLOをTerraformでコード管理することにしました。
本記事では、NewRelicの Service Level 機能をTerraformで管理する方法を紹介します。筆者のチームでは現在この構成をPoC段階で検証中です。試行錯誤の過程も含めてお伝えします。
なぜTerraformで管理するのか
- 変更がコードレビューされる: SLO目標値の変更がGitLabのMerge Requestとして可視化されます
- 環境間の一貫性: dev/stg/pseudo/prodで同じモジュールを使い、変数だけ差し替えられます
繰り返しになりますが、SLI/SLOは実際の計測値を確認しながら、継続的な改善が必要なものです。
都度NewRelicコンソールから変更していると、運用負荷が大きくオペレーションミスを誘発するため、Terraform資材として管理します。また、今後の拡張性としてCI/CD基盤の恩恵を受けることも考慮しています。
SLIの3分類
筆者のチームでは以下の3種類のSLIを定義し検討を進めています。
| SLI | 判定基準 | 用途 |
|---|---|---|
| 可用性 | HTTP 5xx以外 = 成功 | サービスが応答できているか |
| レイテンシ | 応答時間が閾値以内 = 成功 | ユーザー体験の品質 |
| エラー率 | HTTP 5xx = エラー | 異常の割合 |
可用性SLIの成功イベントを「HTTP 5xx以外」としているのは、可用性が「システムが正常に応答できる状態にあるか」を測る指標であるためです。
4xx系レスポンスはサーバーがリクエストを正常に受信・処理した上で返すクライアント起因のエラーであり、システム自体は稼働しています。そのため、サーバー起因の障害を示す5xx系のみを失敗イベントとして扱っています。
この考え方はGoogle SRE Workbookでも採用されている一般的なプラクティスです。なお、408(タイムアウト)や429(レート制限)など一部の4xx系については、今後の運用データを踏まえて扱いを精査していく予定です。
それぞれをTerraformモジュール化し、API単位で呼び出す設計にしています。
Terraformの記述例
以下はすべて一例です。実際の運用ではサービス名やWHERE句、目標値などを環境や要件に合わせて変数化しています。
可用性SLO
resource "newrelic_service_level" "availability" {
guid = var.entity_guid
name = "${var.service_name} - Availability"
description = "Availability SLO (target: ${var.target}%/${var.time_window_days}d)"
events {
account_id = var.account_id
valid_events {
from = "Transaction"
where = var.valid_where
}
good_events {
from = "Transaction"
where = var.good_where # 例: "appName = 'my-api' AND httpResponseCode < '500'"
}
}
objective {
target = var.target # 例: 99.9
time_window {
rolling {
count = var.time_window_days # 例: 28
unit = "DAY"
}
}
}
}
レイテンシSLO
可用性と構造はほぼ同じで、good_eventsの条件が異なります。
good_events {
from = "Transaction"
where = "${var.valid_where} AND duration < ${var.latency_threshold_sec}"
# duration は秒単位。100ms なら 0.1 と指定します
}
エラー率SLO
エラー率では good_events の代わりに bad_events を使います。
bad_events {
from = "Transaction"
where = var.bad_where # 例: "${var.valid_where} AND httpResponseCode >= '500'"
}
モジュール化のディレクトリ構成
modules/service_level/
├── availability/ # 可用性SLOモジュール
├── latency/ # レイテンシSLOモジュール
└── error_rate/ # エラー率SLOモジュール
environments/
├── dev/ # 開発環境(ベースライン測定用)
├── stg/
├── pseudo/
└── prod/
APIごとにモジュールを呼び出すだけで、SLO定義を追加できます。
# 以下は一例です。entity_guidやservice_name、目標値は環境・APIに応じて変数で管理します
module "accounts_api_latency" {
source = "../../modules/service_level/latency"
entity_guid = local.entity_guid.bff
service_name = "/accounts API"
account_id = local.newrelic_account_id
target = 95.0
time_window_days = 28
latency_threshold_sec = 0.1 # 100ms
valid_where = "appName = 'my-api-bff' AND request.uri LIKE '/accounts%'"
}
APM Transactionに記録されないケース
認証トークン発行のように外部サービスで処理されるAPIは、主要マイクロサービスのAPMがなくTransactionを取得できません。このようなケースでは、CDNアクセスログなど別のデータソースや、経由するマイクロサービスのAPM TransactionをSLIに活用することを検討する必要があります。
valid_events {
from = "Log" # カスタムログイベントを使用
where = "logType = 'cdn_access' AND path = '/hoge/v1/fuga'"
}
NewRelicのService Level機能は Transaction 以外のイベントタイプもSLIのデータソースとして使えるため、計測対象に応じて柔軟に選択できます。
PoC段階での所感
- 目標値は仮置きで始めてよい: まず計測基盤を作り、データで実態を把握してから調整するアプローチが有効です。GoogleのSREプラクティスでは28日間のローリングウィンドウが推奨されており、NewRelicのService Levelでもデフォルトが28日間です。少なくともこの期間のデータを蓄積してから目標値を見直すのが目安になります
- APIごとに特性が異なる: 例えば、参照系はP95 < 100ms、決済系はP95 < 1000msなど、一律の目標は現実的ではありません。APIごとの特性やどのマイクロサービスを経由するか、それらのマイクロサービスがどんな処理をするかなどを確認して、適切な目標値を模索する必要があります
-
ダッシュボードもTerraform管理すると便利:
newrelic_one_dashboardで環境ごとに同じ構成のSLOダッシュボードを自動生成できます
今回は、検証中のNewRelicのService Level機能をTerraformで管理する方法の一例を紹介させていただきました。
今後はError Budget Burn Rate Alertとの連携などを検討しつつ、本番環境への展開を進めていく予定です。
参考リンク
- New Relic Service Level Management
- Terraform newrelic_service_level
- Google - SRE Workbook: Implementing SLOs
- Google Cloud Blog - 適切な SLO を設計する方法
みんなの銀行、ゼロバンク・デザインファクトリーでは、一緒に働く仲間を募集しています!
より良い体験を届けられる銀行を、一緒に作りませんか?