TT Lab
はじめる
学ぶ 学習パス コース

CNPE — クラウドネイティブプラットフォームエンジニア

プラットフォームは自分自身を何で測るのか

TT Labで続きを見る

一言でいうと

プラットフォームチームが測るべきものは、ノードのCPUではなく、プラットフォームがユーザーにした約束です。セルフサービスのリクエストが成功する割合、デプロイが終わるまでにかかる時間、元に戻す必要があったデプロイの割合が、その約束です。

なぜリソースのメトリクスでは足りないのか

ノードのメトリクスだけを見るダッシュボードは、インシデントが起きても緑ランプのままです。セルフサービスの払い出しがすべて失敗しても、ノードのCPUはむしろ暇だからです。逆に、ノードが忙しくても、ユーザーから見れば何も問題がないこともあります。

そこで、プラットフォームも1つのサービスとして扱います。ユーザーは開発チームで、リクエストは申請の作成やデプロイであり、成功と失敗があり、所要時間があります。こうすると、測るものがはっきりします。

何を測るか なぜそれなのか
払い出しリクエストの成功割合 セルフサービスが本当にセルフサービスになっているか
リクエストから使用可能になるまでの時間 ゴールデンパスが本当に速いか
デプロイ頻度と、元に戻した割合 デプロイが怖いものかどうか
インシデントの復旧までにかかった時間 問題に気づくまでにかかる時間と、直すまでにかかる時間

どう動くのか

レコーディングルールが先で、アラートがそのあとです

割合をアラートの条件の中で毎回計算すると、同じ式が複数のアラートに散らばります。1か所を直して、ほかの場所を忘れるというミスが、ここで起きます。そのため、割合はレコーディングルールで一度だけ定義し、アラートはその名前を参照します。

groups:
  - name: platform-slo
    rules:
      - record: platform:provision_success:ratio5m
        expr: |
          sum(rate(platform_provision_total{result="success"}[5m]))
          /
          sum(rate(platform_provision_total[5m]))

名前に5mが含まれているなら、式の区間も5分でなければなりません。名前と中身がずれると、そのメトリクスを使うすべての人が、誤った前提で判断することになります。

発火までの待ち時間は目的に合わせて決めます

forは、条件が維持される時間を要求します。このラボは10分を使いますが、すぐに対応しなければならない出来事では、省略することもあります。この時間は、Alertmanagerの送信・繰り返しの間隔とは別のものです。アラートの式は、偽のときに系列を取り除く必要があります。vector(0)や비율 < bool 0.95(プレースホルダーは割合です)は、値が0でも系列が残り、アラートが有効になってしまう落とし穴です。公式アラートルールの説明で、pendingとfiringを区別して読んでください。

runbook_urlがないアラートも同じです。午前3時に受け取ったアラートに、次の行動が書かれていなければ、それは情報ではなくノイズです。severityラベルはルーティングが分かれる基準なので、なければすべてのアラートが同じ経路に流れます。

検証したものとデプロイしたものが同じである必要があります

ルールファイルは、promtool check rulesで検証できます。人が読んでも、式の括弧1つは見つけられません。ただし、検証したファイルと、クラスターに上げたPrometheusRuleが別のものなら、その検証は何も保証しません。ファイルからCRを作り、上げたあとにspec.groups全体を突き合わせます。名前だけが同じで式が変わっていれば、別のルールです。APIが保存したからといって、Operatorが選択した、あるいはPrometheusがロードしたと断定しません。今回の環境はOperatorを実行しないため、保存の一致まで検証し、アラートの配信をテストしたとは主張しません。

現場での姿

仮想の事例を考えてみましょう。失敗の経路がメトリクスを残さない払い出しサービスを作った場合、ダッシュボードには成功率100%しか見えないことがあります。分母が成功だけを数えていれば、割合は常に1です。

割合1つだけでは、このような計装の漏れを見分けにくいです。何を数えているかを、式から直接読んで初めて見えます。そのため、新しいメトリクスを作るときは、失敗をわざと一度起こしてみて、その値が動くかを確認する必要があります。アラートも同じです。

文法のあとに、シナリオを入れます

上の単純な割合は、2つの結果の系列がどちらも存在する場合の出発点です。失敗の系列だけがあれば分子が空になり、トラフィックがなければ分母が0になります。続くラボでは、失敗だけがあるときは分子を0で補いつつ、全体のrateが正のときだけ割合を残します。観測の空白は、成功100%ではなく、別の計装の異常として調べる必要があります。インスタンスごとの成功率を単純に平均すると、リクエスト1件のサーバーと1万件のサーバーを同じ重さで数える誤りが生じます。

rateの公式説明に沿って、カウンターごとのrateを先に計算してから合算します。合計を先に作ってからrateを計算すると、1つの系列の再起動が別の系列の増加と混ざり、リセットの解釈が変わります。ラボは、成功カウンターだけが再起動するシナリオを、リセット区間の中でも検査します。

この過程で使う13個のシナリオは、正常99%、継続する失敗80%、境界95%とその前後、3分の障害、障害後の回復、無トラフィック、観測なし、成功だけがある場合、失敗だけがある場合、カウンターのリセット、リクエスト量が異なる2つのインスタンスです。回復17分の成功率と19分の解除も確認して、5分の区間を10分に変えてしまう誤りを見分けます。これは学習用の固定データによるテストであり、あらゆる本番トラフィックに対する証明ではありません。

promtool check rulesは文法を、promtool test rulesは仮想の時系列での値を検査します。公式テスト形式のinput_seriesとeval_timeを読み、実際の待ち時間と区別してください。イメージの3.0.1は、最新のドキュメントのfuzzy_compareをサポートしないため、ヘルパーは割合の誤差を1e-9未満で直接検査します。

その次に読むこと

メトリクスが異常を知らせたあと、その異常をまず何を数えて分類するのかを、続けて見ます。