mcpField
O
oodle-log-metrics

oodle-log-metrics

github.com/oodle-aiクラウド・DevOps0125 回インストール3 週間前に更新
リポジトリ

oodle-log-metrics について

oodle-log-metricsは、ログ行をメトリクスに変換するルール作成をエージェントに案内するスキルです。フィルターの検証、ラベルのカーディナリティ管理、更新時の既存ルール保持を重視します。

主な機能

  1. 01ルール作成前のログフィルター検証
  2. 02ラベルのカーディナリティ推定
  3. 03カウント、カウンター、ゲージ、ヒストグラムの定義
  4. 04正規表現によるラベルと値の抽出
  5. 05更新前の既存ルール取得

活用シーン

  1. 01一致するログ行のメトリクス化
  2. 02ログイベントからのアラート作成
  3. 03プレーンテキストログのツール遅延測定

インストール

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

$npx skills add https://github.com/oodle-ai/agent-skills --skill oodle-log-metrics

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

詳細

Oodle Log Metrics — ルールとカーディナリティ

このスキルでは、ログストリームを安全にメトリクスへ変換する方法を説明します。フィルターを検証し、labels を絞り込み、カーディナリティの高い時系列を作成しないようにします。ログメトリクスルールは、ログ行内の値をカウントしたり、その値についてアラートを出したりする方法でもあります。モニターは、ルールが出力するメトリクスに対してアラートを出します。

前提条件

brew install oodle-ai/oodle/oodle
oodle configure

ログメトリクスのエンドポイントが動作することを確認します。

oodle log-metrics list -o json | jq 'length'

コマンドの実行順序

oodle コマンドを実行する前に、次の手順を実行してください。

  1. ルールのフィルターと labels がすでにコンテキストにあるか確認します。
  2. ない場合は、サンプルログクエリを実行し(例:oodle logs query。oodle-logs スキルまたはログエクスプローラーを参照)、フィルターに実際に一致するログがあることを確認します。
  3. カーディナリティを見積もります。各ラベルの異なる値の数を掛け合わせます。
  4. フィルターの検証後にのみ、oodle log-metrics create -f rule.json を実行します。
  5. 既存のルールを取得するために get を実行せずに、update を実行しないでください。

クイックリファレンス

タスクコマンド
ルールの一覧表示oodle log-metrics list -o json
ルールの取得oodle log-metrics get <id> -o json
ルールの作成oodle log-metrics create -f rule.json
ルールの更新oodle log-metrics update <id> -f rule.json
ルールの削除oodle log-metrics delete <id> --force

一般的な操作

ルールのスキーマ
{
  "name": "http_errors_from_logs",
  "filter": {
    "all": [
      {"field": "level", "operator": "is", "value": "error"},
      {"field": "service", "operator": "is", "value": "api"}
    ]
  },
  "labels": [
    {"name": "service", "valueExtractor": {"field": "service"}},
    {"name": "env", "valueExtractor": {"field": "env"}}
  ],
  "metricDefinitions": [
    {"name": "http_errors", "type": "log_count"}
  ]
}

フィールドの意味:

フィールド意味
nameルールを識別する名前です。必須です。
filterルールが読み取るログ行を指定します。条件 {"field", "operator", "value", "jsonPath"}、または {"all": [...]}(AND)、{"any": [...]}(OR)、{"not": <filter>} を指定します。これらはネストできます。演算子は is、contains、matches regex、exists です。!= はありません。not を使用してください。
labels出力するメトリクスに追加されるラベルです。それぞれに name と静的な value、または valueExtractor {"field", "jsonPath", "regex"} を指定します。
metricDefinitions出力するメトリクスです。少なくとも1つ必要です。それぞれに name と type を指定します。log_count(一致した行数)、counter(値の合計)、gauge(最後の値)、histogram(値の分布)を指定できます。counter、gauge、histogram は、field から値を読み取り、任意で jsonPath または regex を指定できます。
  • field はログのトップレベルフィールドです。使用できるのは英字、数字、アンダースコアのみです。ネストされた JSON 値を読み取るには、たとえば {"field": "log", "jsonPath": "user.id"} のように jsonPath を使用します。
  • regex では Rust の構文を使用します。キャプチャグループ1が値になるため、必要な部分を1つのグループで囲みます。JSON では、各バックスラッシュをエスケープします。\d は "\\d" です。
  • 正規表現が行に一致しない場合、ラベルは空になり、値は 0 になります。そのため、値を含む行だけを選択するフィルターを指定してください。
  • 出力されるメトリクス名は oodle_logs_<name>(oodle_logs_http_errors)です。histogram は _bucket、_sum、_count の各時系列を出力します。log_count と counter のクエリには increase(...) または rate(...) を使用し、sum by (...) で集計します。
  • ルールは、作成後に到着したログにのみ適用されます。過去のデータには oodle logs query を使用してください。
  • 例のように、all リストには条件を1つだけ指定します。この形式はすべての CLI およびサーバーのバージョンで動作します。
ルールの作成
# ✅ CORRECT — validate filter first, then create
# (preview with the log explorer or `oodle logs query`)
oodle log-metrics create -f rule.json

# ❌ WRONG — creating with an untested filter; the resulting metric is silently empty
oodle log-metrics create -f <(echo '{"name":"x","filter":{"all":[{"field":"levl","operator":"is","value":"eror"}]},"metricDefinitions":[{"name":"x","type":"log_count"}]}')
ルールの更新
# ✅ CORRECT — get → edit → update
oodle log-metrics get lm_123 -o json > rule.json
jq '.labels = [{"name":"service","valueExtractor":{"field":"service"}},{"name":"env","valueExtractor":{"field":"env"}}]' rule.json > rule.new.json
oodle log-metrics update lm_123 -f rule.new.json

# ❌ WRONG — partial payload removes existing fields (and has no `id`, so it is rejected)
oodle log-metrics update lm_123 -f <(echo '{"labels":[{"name":"service","valueExtractor":{"field":"service"}}]}')
ルールの削除
# ✅ CORRECT — verify and delete
oodle log-metrics get lm_123 -o json > /dev/null
oodle log-metrics delete lm_123 --force

# ❌ WRONG — speculative delete by name match
oodle log-metrics delete "$(oodle log-metrics list | grep errors | awk '{print $1}')" --force
ログ行のアラート設定

モニターはログクエリではなく、PromQL を実行します。ログ行に対してアラートを設定するには、ログメトリクスルールを作成し、そのルールが出力するメトリクスを対象とするモニターを作成します(oodle-monitors スキルを参照)。ルールは正規表現で未加工の行テキストを読み取るため、プレーンテキストの行で機能し、ログ変換は不要です。行から抽出したラベル(ユーザー、ツール、テナント)が、アラートの系列名になります。

例:次のような行から、クレジットが切れたユーザーごとにアラートを発生させます。

2026-10-07T10:12:03Z WARN credit exhausted for user=alice plan=pro

credit-exhausted.json:

{
  "name": "credit-exhausted",
  "filter": {"all": [{"field": "message", "operator": "contains", "value": "credit exhausted"}]},
  "labels": [
    {"name": "user", "valueExtractor": {"field": "message", "regex": "user=(\\S+)"}}
  ],
  "metricDefinitions": [{"name": "credit_exhausted", "type": "log_count"}]
}

credit-exhausted-monitor.json(op の 2 は > です):

{
  "name": "Credit exhausted",
  "promql_query": "sum by (user) (increase(oodle_logs_credit_exhausted[10m]))",
  "conditions": {"critical": {"op": 2, "value": 0}},
  "labels": {"team": "billing", "env": "prod"},
  "annotations": {"summary": "User {{ $labels.user }} ran out of credit"}
}
oodle log-metrics create -f credit-exhausted.json
oodle monitors create -f credit-exhausted-monitor.json
# Later: whose credit ran out in the last 24 hours
oodle metrics query --query 'sum by (user) (increase(oodle_logs_credit_exhausted[24h])) > 0' -o json

この場合、ユーザーごとにラベルを付けても問題ありません。イベントの発生頻度が低いためです(「labels はカーディナリティの低いラベルを 2~3 個にする」を参照)。

例:tool Bash ok in 12345 ms の継続時間のように、行内の値を使用する場合です。値ごとにキャプチャグループを 1 つ含む正規表現を 1 つ使い、値を必須とするフィルターを指定します。

{
  "name": "tool-latency",
  "filter": {"all": [{"field": "message", "operator": "matches regex", "value": "tool \\S+ (?:ok|failed) in \\d+ ms"}]},
  "labels": [
    {"name": "tool", "valueExtractor": {"field": "message", "regex": "tool (\\S+) "}},
    {"name": "status", "valueExtractor": {"field": "message", "regex": " (ok|failed) in "}}
  ],
  "metricDefinitions": [
    {"name": "tool_calls", "type": "log_count"},
    {"name": "tool_duration_ms", "type": "histogram", "field": "message", "regex": " in (\\d+) ms"}
  ]
}
# p95 tool latency in ms, per tool
histogram_quantile(0.95, sum by (le, tool) (rate(oodle_logs_tool_duration_ms_bucket[5m])))
# failed calls per tool
sum by (tool) (increase(oodle_logs_tool_calls{status="failed"}[10m]))

ベストプラクティス

ルールを作成する前に、実際のログ量に対して filter を検証する

フィルターのタイプミス(levl=eror)があると、ルールはデータポイントをひそかに 0 件出力します。

# ✅ CORRECT — preview matching log volume in the log explorer first;
# only then run `oodle log-metrics create`
# (or run `oodle logs query` with the same condition and confirm count > 0)

# ❌ WRONG — create the rule, then notice the dashboard panel is empty next week
oodle log-metrics create -f rule.json
labels はカーディナリティの低いラベルを 2~3 個にする

ラベルごとに時系列数が増加します。request_id、user_id、trace_id、(ID を含む)path は避けてください。クレジット拒否のようなまれなイベントに限り、ユーザーラベルを使用できます。

# ✅ CORRECT — bounded labels
"labels": [{"name": "service", "valueExtractor": {"field": "service"}}, {"name": "env", "valueExtractor": {"field": "env"}}]

# ❌ WRONG — `user_id` on every request blows up cardinality (one series per user)
"labels": [{"name": "service", "valueExtractor": {"field": "service"}}, {"name": "user_id", "valueExtractor": {"field": "user_id"}}]
フィールドを保持するため、必ず update の前に get を実行する

update はドキュメントを置き換えます。フィールドを 1 つだけ送信すると、それ以外はすべて null になります。

# ✅ CORRECT
oodle log-metrics get lm_123 -o json > rule.json
jq '.filter.all += [{"field": "status", "operator": "matches regex", "value": "^5"}]' rule.json > rule.new.json
oodle log-metrics update lm_123 -f rule.new.json

# ❌ WRONG — clobbers labels and metricDefinitions
oodle log-metrics update lm_123 -f <(echo '{"filter":{"all":[{"field":"level","operator":"is","value":"error"}]}}')
安定した説明的なメトリクス名を使用する

出力される名前は oodle_logs_<name> です。<domain>_<measurement> という名前にすると、ダッシュボードやドロップルールでメトリクスを簡単に見つけられます。使用できるのは英字、数字、アンダースコアのみです。

# ✅ CORRECT
"metricDefinitions": [{"name": "http_errors", "type": "log_count"}]

# ❌ WRONG — generic name collides with other rules
"metricDefinitions": [{"name": "errors", "type": "log_count"}]

エラーへの対処

エラー原因解決方法
401 UnauthorizedAPI キーが無効または未設定oodle configure を実行するか、OODLE_API_KEY を設定します
404 Not Foundログメトリクスルール ID が存在しないoodle log-metrics list -o json で確認します
connection refusedOODLE_DEPLOYMENT の URL が誤っているOODLE_DEPLOYMENT 環境変数を確認します
400 Match must have a valid Operator演算子が is、contains、matches regex、exists のいずれでもない4 つのいずれかを使用します。「等しくない」場合は、条件を not で囲みます
400 Field ... must contain only alphanumeric characters and underscoresfield にドットを含むフィールド名が指定されているトップレベルのフィールドを使用し、パスは jsonPath に指定します
400 Regex ... is not a valid rust regex正規表現の構文エラー、または JSON のエスケープ漏れJSON 内のバックスラッシュをエスケープします(\\d)。後読み・先読みは使用できません
400 'logCount' metric definition has a Field, JSONPath, or Regexlog_count に field、jsonPath、または regex が指定されているこれらを削除します
400 Log Metrics ID in path and body don't match本文の id がないか、<id> と異なるget を実行し、その出力を編集します
メトリクスは存在するがデータポイントがないフィルターがどのログにも一致しない、またはルール作成後に新しい行がないログエクスプローラーまたは oodle logs query でフィルターを再テストし、フィールド名がログスキーマと一致することを確認します。ルールは過去のログを補完しません
ラベルが空/値がすべて 0正規表現が一致しない、またはグループ 1 が数値ではないサンプル行で正規表現をテストし、値を必須とするフィルターにします
UI にカーディナリティアラームが表示されるlabels にカーディナリティの高いフィールドが含まれているルールを編集してそのラベルを削除します。古い系列は通常の保持期間が経過すると消滅します
429 Too Many Requestsルールの一括作成--retries 3 を追加し、作成頻度を毎秒 10 件未満に抑えます

参考資料

コメント