mcpField
P
promql-generator

promql-generator

github.com/akin-ozerクラウド・DevOps329621 回インストール16 週間前に更新
リポジトリ

promql-generator について

promql-generatorは、ダッシュボード、アラート、メトリクス分析向けのPromQLクエリを作成するスキルです。対話形式で目標、メトリクス、ラベル、パラメーターを確認してからクエリを生成します。

主な機能

  1. 01監視目標と用途の確認
  2. 02メトリクス型と利用可能なラベルの特定
  3. 03対話形式でクエリ条件を計画
  4. 04文書化されたパターンでクエリを生成
  5. 05クエリ結果の検証と調整

活用シーン

  1. 01PromQLのダッシュボードクエリを作成
  2. 02アラートや記録ルールの式を作成
  3. 03トラブルシューティングや容量計画向けのメトリクス分析

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/akin-ozer/cc-devops-skills --skill promql-generator

インストール後、Claude Code で/promql-generatorを入力して読み込まれたか確認します。

同梱ファイル

SKILL.md と一緒にインストールされる参考資料やスクリプト。

examples/
alerting_rules.yaml
common_queries.promql
kubernetes_patterns.promql
recording_rules.yaml
red_method.promql
slo_patterns.promql
use_method.promql
references/
best_practices.md
metric_types.md
promql_functions.md
promql_patterns.md
tests/
test_service_down_portability.py
test_time_window_semantics.py

詳細

PromQL クエリー生成ツール

概要

このスキルでは、ベストプラクティスを組み込んだ、本番環境ですぐに使える PromQL クエリーを生成するための、包括的で対話型のワークフローを提供します。ユーザーとの協力と、コード生成前の計画を重視しながら、モニタリングダッシュボード、アラートルール、アドホック分析用のクエリーを生成します。

このスキルを使用する場面

次のような場合にこのスキルを呼び出します。

  • PromQL クエリーをゼロから新規作成するとき
  • モニタリングダッシュボード(Grafana、Prometheus UI など)を作成するとき
  • Prometheus Alertmanager のアラートルールを実装するとき
  • トラブルシューティングやキャパシティプランニングのためにメトリクスを分析するとき
  • モニタリング要件を PromQL 式に変換するとき
  • PromQL を学習したり、ほかの人に教えたりするとき
  • ユーザーが PromQL クエリーの「作成」「生成」「構築」「記述」を依頼するとき
  • Prometheus のメトリクス(カウンター、ゲージ、ヒストグラム、サマリー)を扱うとき
  • RED(Rate、Errors、Duration)または USE(Utilization、Saturation、Errors)メトリクスを実装するとき

対話型クエリー計画ワークフロー

重要:このスキルでは、クエリーの生成前に対話型の計画を行うことを重視します。生成するクエリーがユーザーの意図に正確に合致するよう、必ずユーザーと協力しながら計画を進めてください。

PromQL クエリーを生成するときは、次のワークフローに従ってください。

ステージ 1:モニタリングの目標を把握する

ユーザーが何をモニタリング、または測定したいのかを把握することから始めます。要件を集めるために、確認の質問をしてください。

  1. 主な目標:何をモニタリング、または測定しようとしていますか?

    • リクエストレート(1 秒あたりのリクエスト数)
    • エラーレート(失敗したリクエストの割合)
    • レイテンシ/所要時間(応答時間、パーセンタイル)
    • リソース使用量(CPU、メモリ、ディスク、ネットワーク)
    • 可用性/稼働時間
    • キューの深さ、飽和度、スループット
    • カスタムビジネスメトリクス
  2. ユースケース:このクエリーを何に使用しますか?

    • ダッシュボードでの可視化(Grafana、Prometheus UI)
    • アラートルール(しきい値を超えたときに発報)
    • アドホックなトラブルシューティング/分析
    • レコーディングルール(事前計算された集計)
    • キャパシティプランニングまたは SLO の追跡
  3. コンテキスト:ほかに必要な情報はありますか?

    • サービス/アプリケーション名
    • チームまたはプロジェクト
    • 優先度
    • 既存のメトリクスや命名規則

情報が提供されていない場合は、AskUserQuestion ツールを使って情報を集めてください。

質問する場合と推測する場合:ユーザーの最初の依頼で目標、ユースケース、コンテキストがすでに明確に指定されている場合(例:「payment-service の P95 レイテンシが 500ms を超えたときのアラートを作成」)、聞き直す代わりに、回答の中でこれらの詳細を確認してもかまいません。不足している情報や曖昧な情報がある場合にのみ、確認の質問をしてください。

ステージ 2:利用可能なメトリクスを特定する

利用可能で関連性のあるメトリクスを特定します。

  1. メトリクスの確認:利用可能なメトリクスは何ですか?

    • メトリクス名をユーザーに尋ねます
    • 不確かな場合は、一般的な命名パターンを提案します
    • 名前に含まれるメトリクスタイプの識別子を確認します:
      • _total サフィックス → Counter
      • _bucket、_sum、_count サフィックス → Histogram
      • サフィックスなし → Gauge の可能性が高い
      • _created サフィックス → Counter の作成時刻
  2. メトリクスタイプの特定:メトリクスタイプを確認します

    • Counter:累積メトリクスで、増加するかゼロにリセットされるのみです
      • 例:http_requests_total、errors_total、bytes_sent_total
      • 使用する関数:rate()、irate()、increase()
    • Gauge:特定時点の値で、増減します
      • 例:memory_usage_bytes、cpu_temperature_celsius、queue_length
      • 使用する関数:avg_over_time()、min_over_time()、max_over_time()、または関数を使わず直接指定します
    • Histogram:観測値をバケットに分け、累積件数を記録します
      • 例:http_request_duration_seconds_bucket、response_size_bytes_bucket
      • 使用する関数:histogram_quantile()、rate()
    • Summary:事前計算された分位数と、件数および合計値を記録します
      • 例:rpc_duration_seconds{quantile="0.95"}
      • 平均値の計算には _sum と _count を使用します。分位数の平均は計算しないでください
  3. ラベルの確認:これらのメトリクスで利用可能なラベルは何ですか?

    • 一般的なラベル:job、instance、environment、service、endpoint、status_code、method
    • フィルタリングやグループ化で重要なラベルを尋ねます

AskUserQuestion ツールを使用して、メトリクス名、タイプ、利用可能なラベルを確認します。

ステージ 3:クエリパラメーターを決定する

クエリに必要な要件を収集します。

ユーザー指定パラメーターの事前確認

重要:ユーザーが最初のリクエストですでにパラメーターを指定している場合(例:「5-minute window」、「500ms threshold」、「> 5% error rate」)、必ず次のようにしてください。

  1. 指定された値を回答で明示的に確認する
  2. AskUserQuestion で、最初の選択肢を「指定値を使用する」として、指定値を事前入力のデフォルトとして提示する
  3. すでに提供されている情報を再度尋ねず、簡単に確認できるようにする

例:ユーザーが「P95 latency が 500ms を超えたらアラート」と指定した場合は、次を使用します。

AskUserQuestion:
- Question: "Confirm the alert threshold?"
- Options:
  1. "500ms (as specified)" - Use the threshold from your request
  2. "Different threshold" - Let me specify a different value

これにより、ユーザーの入力を尊重し、変更も可能なままワークフローを効率化できます。

  1. 時間範囲:クエリでどの時間範囲を対象にしますか?

    • 現在の瞬時値
    • 時間範囲でのレート([5m]、[1h]、[1d])
    • レート計算の場合、リアルタイムでは通常 [1m] から [5m]、傾向の把握では [1h] から [1d] を使用します
    • 目安:レート範囲はスクレイプ間隔の 4 倍以上にします
  2. ラベルによるフィルタリング:どのラベルでデータをフィルタリングしますか?

    • 完全一致:job="api-server"、status_code="200"
    • 不一致:status_code!="200"
    • 正規表現での一致:instance=~"prod-.*"
    • 複数の条件:{job="api", environment="production"}
  3. 集約:データを集約しますか?

    • 集約なし:すべての時系列をそのまま返します
    • ラベルごとに集約:sum by (job, endpoint)、avg by (instance)
    • ラベルを除外して集約:sum without (instance, pod)、avg without (job)
    • 一般的な集約関数:sum、avg、max、min、count、topk、bottomk
  4. しきい値または条件:特定の条件はありますか?

    • アラートの場合:しきい値(例:エラー率 > 5%)
    • フィルタリングの場合:指定した値を上回る、または下回る時系列のみを表示します
    • 比較の場合:過去のデータと比較します(offset)

AskUserQuestion ツールを使用して、これらのパラメーターを収集または確認します。ユーザーがすでに値(例:「5-minute window」、「> 5%」)を指定している場合は、確認用のデフォルト選択肢として提示します。

ステージ 4:クエリプランを提示する

コードを生成する前に、平易な言葉でクエリプランを提示し、ユーザーに確認を求めます。

## PromQL Query Plan

Based on your requirements, here's what the query will do:

**Goal**: [Describe the monitoring goal in plain English]

**Query Structure**:
1. Start with metric: `[metric_name]`
2. Filter by labels: `{label1="value1", label2="value2"}`
3. Apply function: `[function_name]([metric][time_range])`
4. Aggregate: `[aggregation] by ([label_list])`
5. Additional operations: [any calculations, ratios, or transformations]

**Expected Output**:
- Data type: [instant vector/scalar]
- Labels in result: [list of labels]
- Value represents: [what the number means]
- Typical range: [expected value range]

**Example Interpretation**:
If the query returns `0.05`, it means: [plain English explanation]

**Does this match your intentions?**
- If yes, I'll generate the query and validate it
- If no, let me know what needs to change

AskUserQuestion ツールを使用して、次の選択肢でプランを確認します。

  • "Yes, generate this query"
  • "Modify [specific aspect]"
  • "Show me alternative approaches"

ユーザーが選択した場合:

  • "Modify [specific aspect]":変更する内容(メトリクス、ラベル、関数、時間範囲、しきい値、出力形式)について、焦点を絞った質問を 1 つ行い、生成前に更新したプランを提示します。
  • "Show me alternative approaches":トレードオフ(精度、コスト、カーディナリティ、可読性)を示しながら、少なくとも 2 つの有効なクエリプランを提示し、生成前にユーザーに 1 つ選んでもらいます。
ステージ 5:PromQL クエリを生成する

ユーザーがプランを確認したら、ベストプラクティスに従って実際の PromQL クエリを生成します。

重要:生成前にリファレンスファイルを参照する

クエリコードを書く前に、必ず次の手順を実行してください。

  1. まずクエリのカテゴリ(ヒストグラム、RED、USE、関数固有、最適化など)を特定します。

  2. Read ツールを使用して、関連するリファレンスセクションのみを読みます。

    • ヒストグラムクエリの場合 → references/metric_types.md(Histogram セクション)を読みます
    • エラー/レイテンシのパターンの場合 → references/promql_patterns.md(RED method セクション)を読みます
    • リソース監視の場合 → references/promql_patterns.md(USE method セクション)を読みます
    • 最適化に関する質問の場合 → references/best_practices.md を読みます
    • 特定の関数の場合 → references/promql_functions.md を読みます
    • 要件が変更された場合、またはこのスレッド内でまだ参照していない場合に限り、セクションを再度読みます。
  3. 必要なリファレンスを読めない場合は、その旨を伝え、すでに参照したドキュメント内で最も適切なパターンを使い、最善を尽くして生成を続けます。

  4. 該当するパターンまたはベストプラクティスを回答内で引用します。

    As documented in references/promql_patterns.md (Pattern 3: Latency Percentile):
    # 95th percentile latency
    histogram_quantile(0.95, sum by (le) (rate(...)))
    
  5. 類似のクエリを生成する際は、サンプルファイルを参照します。

    Based on examples/red_method.promql (lines 64-82):
    # P95 latency with proper histogram_quantile usage
    

これにより、反復的なフォローアップのたびにファイル全体を不必要に読み直すことなく、生成するクエリをドキュメント化されたパターンに沿ったものにできます。

クエリ生成のベストプラクティス
  1. 常にラベルフィルターを使用する

    # Good: Specific filtering reduces cardinality
    rate(http_requests_total{job="api-server", environment="prod"}[5m])
    
    # Bad: Matches all time series, high cardinality
    rate(http_requests_total[5m])
    
  2. メトリクスタイプに適した関数を使用する

    # Counter: Use rate() or increase()
    rate(http_requests_total[5m])
    
    # Gauge: Use directly or with *_over_time()
    memory_usage_bytes
    avg_over_time(memory_usage_bytes[5m])
    
    # Histogram: Use histogram_quantile()
    histogram_quantile(0.95,
      sum by (le) (rate(http_request_duration_seconds_bucket[5m]))
    )
    
  3. by() または without() を使って集計を適用する

    # Aggregate by specific labels (keeps only these labels)
    sum by (job, endpoint) (rate(http_requests_total[5m]))
    
    # Aggregate without specific labels (removes these labels)
    sum without (instance, pod) (rate(http_requests_total[5m]))
    
  4. 可能な場合は正規表現より完全一致を使用する

    # Good: Faster exact match
    http_requests_total{status_code="200"}
    
    # Bad: Slower regex match when not needed
    http_requests_total{status_code=~"200"}
    
  5. 比率を正しく計算する

    # Error rate: errors / total requests
    sum(rate(http_requests_total{status_code=~"5.."}[5m]))
    /
    sum(rate(http_requests_total[5m]))
    
  6. 複雑なクエリには記録ルールを使用する

    • クエリが頻繁に使用される場合、または計算コストが高い場合
    • データを事前集計してクエリ負荷を軽減します
    • 命名規則 level:metric:operations に従います
  7. 読みやすい形式にする

    # Good: Multi-line for complex queries
    histogram_quantile(0.95,
      sum by (le, job) (
        rate(http_request_duration_seconds_bucket{job="api-server"}[5m])
      )
    )
    
よく使われるクエリパターン

パターン 1:リクエストレート

# Requests per second
rate(http_requests_total{job="api-server"}[5m])

# Total requests per second across all instances
sum(rate(http_requests_total{job="api-server"}[5m]))

パターン 2:エラーレート

# Error ratio (0 to 1)
sum(rate(http_requests_total{job="api-server", status_code=~"5.."}[5m]))
/
sum(rate(http_requests_total{job="api-server"}[5m]))

# Error percentage (0 to 100)
(
  sum(rate(http_requests_total{job="api-server", status_code=~"5.."}[5m]))
  /
  sum(rate(http_requests_total{job="api-server"}[5m]))
) * 100

パターン 3:レイテンシのパーセンタイル(ヒストグラム)

# 95th percentile latency
histogram_quantile(0.95,
  sum by (le) (
    rate(http_request_duration_seconds_bucket{job="api-server"}[5m])
  )
)

パターン 4:リソース使用量

# Current memory usage
process_resident_memory_bytes{job="api-server"}

# Average CPU usage over 5 minutes
avg_over_time(process_cpu_seconds_total{job="api-server"}[5m])

パターン 5:可用性

# Percentage of up instances
(
  count(up{job="api-server"} == 1)
  /
  count(up{job="api-server"})
) * 100

パターン 6:飽和度/キューの深さ

# Average queue length
avg_over_time(queue_depth{job="worker"}[5m])

# Maximum queue depth in the last hour
max_over_time(queue_depth{job="worker"}[1h])
ステージ 6:生成したクエリを検証する

必ず最初に、devops-skills:promql-validator スキルを使用して生成したクエリの検証を試みてください。

After generating the query, automatically invoke:
Skill(devops-skills:promql-validator)

The devops-skills:promql-validator skill will:
1. Check syntax correctness
2. Validate semantic logic (correct functions for metric types)
3. Identify anti-patterns and inefficiencies
4. Suggest optimizations
5. Explain what the query does
6. Verify it matches user intent

検証チェックリスト:

  • 構文が正しい(括弧の対応、演算子が有効)
  • メトリクスの型が関数の使用方法に合っている
  • ラベルフィルターが十分に具体的
  • 集計方法が適切
  • 時間範囲が妥当
  • 既知のアンチパターンがない
  • クエリのパフォーマンスが最適化されている

検証に失敗した場合は、問題を修正して、すべてのチェックに合格するまで再検証してください。

バリデータースキルを利用できない場合、実行に失敗した場合、または修正と再検証を 2 サイクル行っても完了できない場合:

  • バリデーターの失敗について簡潔に報告してください(ツールを利用できない、タイムアウト、解析エラーなど)。
  • 手動で代替チェックを実行してください(構文の形、メトリクスと関数の互換性、ラベルフィルタリング、集計、時間範囲の妥当性)。
  • チェックできなかった項目には 未検証 と明記し、最善努力による出力で進めるか、別の検証を試みるために追加情報を提供するかをユーザーに尋ねてください。

重要:検証結果をユーザーに表示する

検証の実行後、必ず次の形式で構造化された結果をユーザーに表示してください。

## PromQL Validation Results

### Syntax Check
- Status: ✅ VALID / ⚠️ WARNING / ❌ ERROR / ⚠️ UNVERIFIED
- Issues: [list any syntax errors]

### Best Practices Check
- Status: ✅ OPTIMIZED / ⚠️ CAN BE IMPROVED / ❌ HAS ISSUES / ⚠️ UNVERIFIED
- Issues: [list any problems found]
- Suggestions: [list optimization opportunities]

### Validation Coverage
- Validator tool run: [successful / failed / unavailable]
- Checks completed: [syntax, semantics, anti-patterns, performance, intent-match]
- Checks skipped: [list any skipped checks, or "None"]

### Query Explanation
- **What it measures**: [plain English description]
- **Output labels**: [list labels in result, or "None (scalar)"]
- **Expected result structure**: [instant vector / scalar / etc.]

これにより、ユーザーは検証プロセスと推奨事項を把握できます。

ステージ 7:使用方法を説明する

生成と検証(または手動での代替検証)の後、ユーザーに次の情報を提供してください。

  1. 最終的なクエリ:

    [Generated and validated PromQL query]
    
  2. クエリの説明:

    • クエリで測定する内容
    • 結果の解釈方法
    • 予想される値の範囲
    • 出力に含まれるラベル
  3. 使用方法:

    • ダッシュボードの場合:Grafana/Prometheus UI パネルのクエリにコピーします
    • アラートの場合:しきい値を設定して Alertmanager ルールに組み込みます
    • 記録ルールの場合:Prometheus の記録ルール設定に追加します
    • アドホックの場合:Prometheus の式ブラウザーで直接実行します
  4. カスタマイズに関する注意:

    • 調整が必要になる可能性がある時間範囲
    • 環境に応じて変更するラベル
    • 調整するしきい値
    • 要件が変わった場合の代替関数
  5. 関連クエリ:

    • 補完的なクエリを提案します
    • 記録ルールの活用機会に言及します
    • ダッシュボードのパネルを推奨します

ネイティブヒストグラム(Prometheus 3.x 以降)

ネイティブヒストグラムは Prometheus 3.0 以降(2024 年 11 月リリース)で安定版になりました。従来のヒストグラムに比べて、次の大きな利点があります。

  • 空のバケットにかかるコストがほぼゼロのスパースなバケット表現
  • インストルメンテーション時にバケット境界を設定する必要がない
  • float64 の全範囲をカバー
  • ヒストグラム間の効率的なマージ
  • よりシンプルなクエリ構文

重要:Prometheus v3.8.0 以降、ネイティブヒストグラムは完全な安定版です。ただし、ネイティブヒストグラムのスクレイピングには、scrape_native_histograms 設定による明示的な有効化が引き続き必要です。v3.9 以降はフィーチャーフラグは不要ですが、scrape_native_histograms を明示的に設定する必要があります。

ネイティブヒストグラムと従来のヒストグラムの構文
# Classic histogram (requires _bucket suffix and le label)
histogram_quantile(0.95,
  sum by (job, le) (rate(http_request_duration_seconds_bucket[5m]))
)

# Native histogram (simpler - no _bucket suffix, no le label needed)
histogram_quantile(0.95,
  sum by (job) (rate(http_request_duration_seconds[5m]))
)
ネイティブヒストグラム関数
# Get observation count rate from native histogram
histogram_count(rate(http_request_duration_seconds[5m]))

# Get sum of observations from native histogram
histogram_sum(rate(http_request_duration_seconds[5m]))

# Calculate fraction of observations between two values
histogram_fraction(0, 0.1, rate(http_request_duration_seconds[5m]))

# Average request duration from native histogram
histogram_sum(rate(http_request_duration_seconds[5m]))
/
histogram_count(rate(http_request_duration_seconds[5m]))
ネイティブヒストグラムと従来のヒストグラムの判別

ネイティブヒストグラムは次の特徴で判別できます。

  • メトリクス名に _bucket 接尾辞がない
  • 時系列に le ラベルがない
  • メトリクスにヒストグラムデータが直接格納される(バケットカウンターが別々に格納されるのではない)

クエリを実行する際は、Prometheus インスタンスでネイティブヒストグラムが有効になっているか確認してください。

# prometheus.yml - Enable native histogram scraping
scrape_configs:
  - job_name: 'my-app'
    scrape_native_histogram: true  # Prometheus 3.x+
カスタムバケットネイティブヒストグラム(NHCB)

Prometheus 3.4+ はカスタムバケットネイティブヒストグラム(スキーマ -53)をサポートしており、クラシックヒストグラムからネイティブヒストグラムへの変換が可能です。これは、既存のクラシックヒストグラムを使用しているユーザーにとって重要な移行経路です。

NHCB のメリット:

  • 既存のインストルメンテーションを維持できます(コードの変更は不要です)
  • クラシックヒストグラムをネイティブヒストグラムとして保存し、コストを削減できます
  • ネイティブヒストグラムの構文でクエリできます
  • 信頼性と圧縮率が向上します

設定(Prometheus 3.4+):

# prometheus.yml - Convert classic histograms to NHCB on scrape
global:
  scrape_configs:
    - job_name: 'my-app'
      convert_classic_histograms_to_nhcb: true  # Prometheus 3.4+

NHCB のクエリ:

# Query NHCB metrics the same way as native histograms
histogram_quantile(0.95, sum by (job) (rate(http_request_duration_seconds[5m])))

# histogram_fraction also works with NHCB (Prometheus 3.4+)
histogram_fraction(0, 0.2, rate(http_request_duration_seconds[5m]))

注: スキーマ -53 はカスタムバケット境界を示します。カスタムバケット境界が異なるヒストグラムは、通常、相互にマージできません。


SLO、エラーバジェット、バーンレートのパターン

サービスレベル目標(SLO)は、現代の SRE プラクティスにおいて重要です。これらのパターンは、SLO ベースのモニタリングとアラートの実装に役立ちます。

エラーバジェットの計算
# Error budget remaining (for 99.9% SLO over 30 days)
# Returns value between 0 and 1 (1 = full budget, 0 = exhausted)
1 - (
  sum(rate(http_requests_total{job="api", status_code=~"5.."}[30d]))
  /
  sum(rate(http_requests_total{job="api"}[30d]))
) / 0.001  # 0.001 = 1 - 0.999 (allowed error rate)

# Simplified: Availability over 30 days
sum(rate(http_requests_total{job="api", status_code!~"5.."}[30d]))
/
sum(rate(http_requests_total{job="api"}[30d]))
バーンレートの計算

バーンレートは、エラーバジェットを消費する速度を測定します。バーンレートが 1 の場合、SLO の期間が終了する時点で、ちょうどバジェットを使い切ります。

# Current burn rate (1 hour window, 99.9% SLO)
# Burn rate = (current error rate) / (allowed error rate)
(
  sum(rate(http_requests_total{job="api", status_code=~"5.."}[1h]))
  /
  sum(rate(http_requests_total{job="api"}[1h]))
) / 0.001  # 0.001 = allowed error rate for 99.9% SLO

# Burn rate > 1 means consuming budget faster than allowed
# Burn rate of 14.4 consumes 2% of monthly budget in 1 hour
マルチウィンドウ、マルチバーンレートアラート(Google SRE 標準)

SLO アラートでは、検出速度と精度のバランスを取るために、複数のウィンドウを使用する方法が推奨されています。

# Page-level alert: 2% budget in 1 hour (burn rate 14.4)
# Long window (1h) AND short window (5m) must both exceed threshold
(
  (
    sum(rate(http_requests_total{job="api", status_code=~"5.."}[1h]))
    /
    sum(rate(http_requests_total{job="api"}[1h]))
  ) > 14.4 * 0.001
)
and
(
  (
    sum(rate(http_requests_total{job="api", status_code=~"5.."}[5m]))
    /
    sum(rate(http_requests_total{job="api"}[5m]))
  ) > 14.4 * 0.001
)

# Ticket-level alert: 5% budget in 6 hours (burn rate 6)
(
  (
    sum(rate(http_requests_total{job="api", status_code=~"5.."}[6h]))
    /
    sum(rate(http_requests_total{job="api"}[6h]))
  ) > 6 * 0.001
)
and
(
  (
    sum(rate(http_requests_total{job="api", status_code=~"5.."}[30m]))
    /
    sum(rate(http_requests_total{job="api"}[30m]))
  ) > 6 * 0.001
)
SLO の記録ルール

効率的なアラートのために、SLO メトリクスを事前に計算します。

# Recording rules for SLO calculations
groups:
  - name: slo_recording_rules
    interval: 30s
    rules:
      # Error ratio over different windows
      - record: job:slo_errors_per_request:ratio_rate1h
        expr: |
          sum by (job) (rate(http_requests_total{status_code=~"5.."}[1h]))
          /
          sum by (job) (rate(http_requests_total[1h]))

      - record: job:slo_errors_per_request:ratio_rate5m
        expr: |
          sum by (job) (rate(http_requests_total{status_code=~"5.."}[5m]))
          /
          sum by (job) (rate(http_requests_total[5m]))

      # Availability (success ratio)
      - record: job:slo_availability:ratio_rate1h
        expr: |
          1 - job:slo_errors_per_request:ratio_rate1h
レイテンシ SLO クエリ
# Percentage of requests faster than SLO target (200ms)
(
  sum(rate(http_request_duration_seconds_bucket{le="0.2", job="api"}[5m]))
  /
  sum(rate(http_request_duration_seconds_count{job="api"}[5m]))
) * 100

# Requests violating latency SLO (slower than 500ms)
(
  sum(rate(http_request_duration_seconds_count{job="api"}[5m]))
  -
  sum(rate(http_request_duration_seconds_bucket{le="0.5", job="api"}[5m]))
)
/
sum(rate(http_request_duration_seconds_count{job="api"}[5m]))
バーンレートの参照表
バーンレート消費したバジェット30 日間のバジェットを使い切るまでの時間アラートの重大度
130 日間で 100%30 日間なし
215 日間で 100%15 日間低
66 時間で 5%5 日間チケット
14.41 時間で 2%約 2 日間ページ
361 時間で 5%約 20 時間ページ(緊急)

高度なクエリ手法

サブクエリの使用

サブクエリを使うと、時間に基づく複雑な計算ができます。

# Maximum 5-minute rate over the past 30 minutes
max_over_time(
  rate(http_requests_total[5m])[30m:1m]
)

構文: <query>[<range>:<resolution>]

  • <range>: 評価対象の時間ウィンドウ
  • <resolution>: 評価間のステップ幅
offset 修飾子の使用

現在のデータと過去のデータを比較します。

# Compare current rate with rate from 1 week ago
rate(http_requests_total[5m])
-
rate(http_requests_total[5m] offset 1w)
@ 修飾子の使用

特定のタイムスタンプでメトリクスをクエリします。

# Rate at the end of the range query
rate(http_requests_total[5m] @ end())

# Rate at specific Unix timestamp
rate(http_requests_total[5m] @ 1609459200)
二項演算子とベクトルマッチング

演算子を使ってメトリクスを組み合わせ、ラベルのマッチングを制御します。

# One-to-one matching (default)
metric_a + metric_b

# Many-to-one with group_left
rate(http_requests_total[5m])
* on (job, instance) group_left (version)
  app_version_info

# Ignoring specific labels
metric_a + ignoring(instance) metric_b
論理演算子

条件に基づいて時系列をフィルタリングします。

# Return series only where value > 100
http_requests_total > 100

# Return series present in both
metric_a and metric_b

# Return series in A but not in B
metric_a unless metric_b

ドキュメントの検索

ユーザーが特定の Prometheus の機能、演算子、またはカスタムメトリクスについて質問した場合:

  1. まず context7 MCP を試します(推奨):

    Use mcp__context7__resolve-library-id with "prometheus"
    Then use mcp__context7__get-library-docs with:
    - context7CompatibleLibraryID: /prometheus/docs
    - topic: [specific feature, function, or operator]
    - page: 1 (fetch additional pages if needed)
    
  2. フォールバックとして WebSearch を使用します:

    Search query pattern:
    "Prometheus PromQL [function/operator/feature] documentation [version] examples"
    
    Examples:
    "Prometheus PromQL rate function documentation examples"
    "Prometheus PromQL histogram_quantile documentation best practices"
    "Prometheus PromQL aggregation operators documentation"
    

一般的なモニタリングシナリオ

RED メソッド(リクエスト駆動型サービス向け)
  1. Rate: リクエストスループット

    sum(rate(http_requests_total{job="api"}[5m])) by (endpoint)
    
  2. Errors: エラー率

    sum(rate(http_requests_total{job="api", status_code=~"5.."}[5m]))
    /
    sum(rate(http_requests_total{job="api"}[5m]))
    
  3. Duration: レイテンシのパーセンタイル

    histogram_quantile(0.95,
      sum by (le) (rate(http_request_duration_seconds_bucket{job="api"}[5m]))
    )
    
USE メソッド(リソース向け)
  1. Utilization: リソース使用率

    (
      avg(rate(node_cpu_seconds_total{mode!="idle"}[5m]))
      /
      count(node_cpu_seconds_total{mode="idle"})
    ) * 100
    
  2. Saturation: キューの深さ、またはリソースの競合

    avg_over_time(node_load1[5m])
    
  3. Errors: エラーカウンター

    rate(node_network_receive_errs_total[5m])
    

アラートルール

アラート用のクエリを生成するとき:

  1. しきい値を含める: 条件を明示します

    # Alert when error rate exceeds 5%
    (
      sum(rate(http_requests_total{status_code=~"5.."}[5m]))
      /
      sum(rate(http_requests_total[5m]))
    ) > 0.05
    
  2. ブール演算子を使用する: 1(発火)または 0(アラートなし)を返します

    # Returns 1 when memory usage > 90%
    (process_resident_memory_bytes / node_memory_MemTotal_bytes) > 0.9
    
  3. 継続時間を考慮する: アラートでは通常、for 句を使用します

    alert: HighErrorRate
    expr: |
      (
        sum(rate(http_requests_total{status_code=~"5.."}[5m]))
        /
        sum(rate(http_requests_total[5m]))
      ) > 0.05
    for: 10m  # Only fire after 10 minutes of continuous violation
    

記録ルール

記録ルール用のクエリを生成するとき:

  1. 命名規則に従う: level:metric:operations

    # level: aggregation level (job, instance, etc.)
    # metric: base metric name
    # operations: functions applied
    
    - record: job:http_requests:rate5m
      expr: sum by (job) (rate(http_requests_total[5m]))
    
  2. 負荷の高いクエリを事前に集計する:

    # Recording rule for frequently-used latency query
    - record: job_endpoint:http_request_duration_seconds:p95
      expr: |
        histogram_quantile(0.95,
          sum by (job, endpoint, le) (
            rate(http_request_duration_seconds_bucket[5m])
          )
        )
    
  3. ダッシュボードで記録済みのメトリクスを使用する:

    # Instead of expensive query, use pre-recorded metric
    job_endpoint:http_request_duration_seconds:p95{job="api-server"}
    

エラー処理

よくある問題と解決策
  1. 結果が空の場合:

    • メトリクスが存在するか確認します:up{job="your-job"}
    • ラベルフィルターが正しいことを確認します
    • 時間範囲が適切であることを確認します
    • メトリクスがスクレイプされていることを確認します
  2. 時系列が多すぎる場合(カーディナリティが高い場合):

    • より具体的なラベルフィルターを追加します
    • 集約を使って時系列の数を減らします
    • 記録ルールの使用を検討します
    • ラベルの爆発的な増加(動的ラベル)がないか確認します
  3. 値が正しくない場合:

    • メトリクスの種類(カウンターかゲージか)を確認します
    • 関数の使い方を確認します(ゲージではなく、カウンターに対して rate を使います)
    • 時間範囲が適切であることを確認します
    • カウンターのリセットがないか確認します
  4. パフォーマンスに関する問題:

    • レンジベクトルの時間範囲を短くします
    • ラベルフィルターを追加してカーディナリティを下げます
    • 複雑なクエリには記録ルールを使います
    • 負荷の高い正規表現パターンを避けます
    • クエリのタイムアウト設定を検討します

コミュニケーションのガイドライン

クエリを生成する際は、次の点に従います。

  1. 計画を説明する:生成する前に、必ず平易な英語で計画を提示します
  2. 質問する:AskUserQuestion ツールを使って要件を収集します
  3. 意図を確認する:最終決定の前に、クエリがユーザーの目標に合っていることを確認します
  4. 説明する:特定の関数やパターンを使う理由を説明します
  5. 背景を示す:結果の解釈方法を示します
  6. 改善案を提案する:最適化や別のアプローチを提示します
  7. 先回りして検証する:必ず検証し、問題があれば修正します
  8. フォローアップする:調整が必要かどうか尋ねます

AskUserQuestion を利用できない場合のフォールバック

構造化された質問ツールを利用できない場合は、プレーンテキストで明示的な質問票をインラインで提示し、続行します。

  1. 目的、メトリクス名/種類、ラベル、時間範囲、集約、ユースケースを、簡潔な質問1つにまとめて尋ねます。
  2. ユーザーから部分的な回答しか得られない場合は、慎重なデフォルト値を使って続行し、仮定を明示します。
  3. 中核となる入力情報がまだ曖昧な場合は、具体的なクエリ計画を2~3案提示し、どれを選ぶかユーザーに尋ねます。
  4. 完全な情報がそろうまで生成を無期限に保留しないでください。仮定を明記したうえで、可能な範囲で最善のクエリを生成します。

関連するリファレンスの参照基準と簡単なケースでの省略ルール

リファレンスは決められた基準に従って使用しますが、簡単なリクエストでは不要な読み込みを避けます。

次のいずれかに該当する場合は、リファレンスを読みます。

  • ヒストグラムまたはサマリーの分位数が求められている
  • クエリで結合/ベクトルマッチング、サブクエリ、オフセット、記録ルール/アラートルールを使う
  • SLO/バーンレート/エラーバジェットのワークフロー用のクエリである
  • クエリに最適化またはカーディナリティに関する懸念が含まれている
  • メトリクスの種類が不明、または意見が分かれている

次のすべてに該当する場合に限り、リファレンスの読み込みを省略します。

  • 単一メトリクス、単一関数のクエリ(rate、increase、sum、avg、max、min)
  • 結合、記録ルール/アラートルール、高度な関数がない
  • メトリクスの種類とラベルがユーザーから明確に提示されている

省略する場合は、必ず Reference read skipped (trivial case) と明示し、検証は必須とします。

devops-skills:promql-validator との統合

PromQL クエリを生成した後は、品質を確保するため、devops-skills:promql-validator スキルを自動的に呼び出します。

Steps:
1. Generate the PromQL query based on user requirements
2. Invoke devops-skills:promql-validator skill with the generated query
3. Review validation results (syntax, semantics, performance)
4. Fix any issues identified by the validator
5. Re-validate until all checks pass
6. Provide the final validated query with usage instructions
7. Ask user if further refinements are needed

これにより、生成されるすべてのクエリがベストプラクティスに従い、本番環境ですぐに使える状態になります。

リソース

重要:リファレンスを明示的に参照すること

クエリを生成する際は、Read ツールを使って関連するリファレンスファイルを明示的に読み込み、該当するベストプラクティスを引用することを推奨します。これにより、生成されるクエリが文書化されたパターンに従うようになり、推奨されるアプローチの理由をユーザーが理解しやすくなります。

references/

promql_functions.md

  • すべての PromQL 関数を網羅したリファレンス
  • カテゴリ別(集約、数学、時間、ヒストグラムなど)に分類
  • 各関数の使用例
  • このファイルを読む場合:特定の関数要件を実装するとき、または関数の動作についてユーザーから質問されたとき

promql_patterns.md

  • 一般的な監視シナリオ向けのよく使われるクエリパターン
  • RED メソッドのパターン(Rate、Errors、Duration)
  • USE メソッドのパターン(Utilization、Saturation、Errors)
  • アラートと記録ルールのパターン
  • このファイルを読む場合:エラー率、レイテンシ、リソース使用量など、標準的な監視パターンを実装するとき

best_practices.md

  • PromQL のベストプラクティスとアンチパターン
  • パフォーマンス最適化のガイドライン
  • カーディナリティ管理
  • クエリ構成に関する推奨事項
  • このファイルを読む場合:クエリを最適化するとき、アンチパターンがないか確認するとき、またはカーディナリティに関する懸念が生じたとき

metric_types.md

  • Prometheus のメトリクスタイプに関する詳細ガイド
  • Counter、Gauge、Histogram、Summary
  • 各タイプを使用する場面
  • 各タイプに適した関数
  • このファイルを読む場合:メトリクスタイプに関する質問に答えるとき、またはメトリクスに適した関数を判断するとき
examples/

common_queries.promql

  • よく使われる PromQL クエリ集
  • リクエスト率、エラー率、レイテンシのクエリ
  • リソース使用量のクエリ
  • 可用性と稼働時間のクエリ
  • コピーしてカスタマイズできます

red_method.promql

  • RED メソッドの完全な実装
  • リクエスト率のクエリ
  • エラー率のクエリ
  • 継続時間/レイテンシのクエリ

use_method.promql

  • USE メソッドの完全な実装
  • 使用率のクエリ
  • 飽和度のクエリ
  • エラーのクエリ

alerting_rules.yaml

  • Prometheus アラートルールの例
  • さまざまなしきい値ベースのアラート
  • アラート式のベストプラクティス

recording_rules.yaml

  • Prometheus 記録ルールの例
  • 事前集約されたメトリクス
  • 命名規則

slo_patterns.promql

  • SLO、エラーバジェット、バーンレートのクエリ
  • マルチウィンドウ、マルチバーンレートのアラートパターン
  • レイテンシの SLO 適合性クエリ

kubernetes_patterns.promql

  • Kubernetes の監視パターン
  • kube-state-metrics のクエリ(ポッド、デプロイメント、ノード)
  • cAdvisor のコンテナメトリクス(CPU、メモリ)
  • Kubernetes 向けのベクトルマッチングと結合

重要な注意事項

  1. 必ず対話しながら計画する:ユーザーと計画を確認する前にクエリを生成しないでください
  2. AskUserQuestion を使用する:ツールを活用して要件を収集し、計画を確認してください
  3. すべてを検証する:生成後は必ず devops-skills:promql-validator を呼び出してください
  4. ユーザーに説明する:クエリが何を行うのか、なぜそのような構成なのかを説明してください
  5. ユースケースを考慮する:ダッシュボード、アラート、分析のどれに使うかに応じてクエリを調整してください
  6. パフォーマンスを考慮する:必ずラベルフィルターを含め、カーディナリティを考慮してください
  7. メトリクスタイプに従う:カウンター、ゲージ、ヒストグラムに適した関数を使用してください
  8. 読みやすく整形する:複雑なクエリには複数行の形式を使用してください

成功基準

クエリ生成セッションが成功したと判断するには、以下の測定可能なチェックポイントを満たす必要があります。

  1. 要件の把握が完了:目標/ユースケース/メトリクス/時間範囲/集約方法を記録している
  2. 計画の確認が完了:ユーザーが計画を承認している、または明示的な前提条件を記録している
  3. 参照資料の判断を記録:ファイル名とともに consulted、または理由とともに skipped (trivial case) を記録している
  4. クエリの妥当性確認が完了:構文がバリデーターに合格している、または手動での代替確認が完了している
  5. 意味的な妥当性確認が完了:関数の選択がメトリクスタイプ(counter/gauge/histogram/summary)に適合している
  6. カーディナリティへの対策が完了:クエリに明示的なフィルター、または集約の根拠が含まれている
  7. 提供が完了:最終的なクエリ、解釈、次のカスタマイズに関するガイダンスを提示している

覚えておくこと

目標は、ユーザーの意図に正確に合致する PromQL クエリを共同で計画し、生成することです。常に明確さ、正確さ、パフォーマンスを優先してください。対話型の計画フェーズはこのスキルで最も重要な部分です。決して省略しないでください!

コメント