mcpField
O
oodle-drop-rules

oodle-drop-rules

github.com/oodle-aiCloud & DevOps0125 installsUpdated 3w ago
Repository

About oodle-drop-rules

oodle-drop-rules is a skill for agents managing metric drop rules through the Oodle CLI, aimed at teams controlling costs from high-volume metrics. It stresses impact estimates, narrow initial rules in non-production environments, and checking dashboard and monitor dependencies.

Key features

  1. 01List, read, create, update, and delete rules
  2. 02Match series by metric name and labels
  3. 03Estimate affected series before rule creation
  4. 04Start with narrow rules in non-production
  5. 05Read full rules before updates to preserve fields

Use cases

  1. 01Estimate the scope of dropping high-volume metrics
  2. 02Trial a single-metric rule in staging
  3. 03Check whether dashboards or monitors depend on a metric
  4. 04Adjust matchers to control data ingestion

Install

Copy the command and run it in a terminal.

$npx skills add https://github.com/oodle-ai/agent-skills --skill oodle-drop-rules

After installing, type/oodle-drop-rulesin Claude Code to confirm it loaded.

Details

From the project README

Oodle Drop Rules — Cost Control

This skill teaches the agent to drop high-volume metrics safely: estimate the impact first, start with a narrow rule, and never silently delete a metric a dashboard depends on. There is no sampling mode: a rule drops every series that it matches, and dropped data cannot be recovered.

Prerequisites

brew install oodle-ai/oodle/oodle
oodle configure

Confirm the drop-rules endpoint works:

oodle drop-rules list -o json | jq 'length'

Command Execution Order

Before running any oodle command:

  1. Check whether the target metric prefix and matchers are already in context.
  2. If not, run oodle metrics query --query 'count({__name__=~"<prefix>.*"})' -o json to estimate impact.
  3. Confirm no critical dashboards or monitors depend on the affected series (see "Estimating impact before creating a rule").
  4. Start with a narrow rule (one metric, one non-production env) on the first attempt; widen the filters only after the dashboards and monitors of that env show no regression.
  5. Run oodle drop-rules create -f rule.json.

Quick Reference

TaskCommand
List rulesoodle drop-rules list -o json
Get ruleoodle drop-rules get <id> -o json
Create ruleoodle drop-rules create -f rule.json
Update ruleoodle drop-rules update <id> -f rule.json
Delete ruleoodle drop-rules delete <id> --force

Common Operations

Rule schema
{
  "rule_name": "drop-noisy-debug-metrics",
  "metric_name": {"type": 2, "name": "__name__", "value": "debug_.*"},
  "filters": [
    {"type": 0, "name": "level", "value": "debug"},
    {"type": 0, "name": "env",   "value": "staging"}
  ],
  "type": "series"
}
FieldMeaning
rule_nameRequired. Name of the rule
metric_nameMatcher on the metric name ("name": "__name__")
filtersLabel matchers. All must match for the rule to fire (logical AND)
typeRequired. Must be "series"

Matcher type: 0 equals, 1 not equals, 2 regex match, 3 regex not match.

Estimating impact before creating a rule
# ✅ CORRECT — count series that will be affected
oodle metrics query --query 'count({__name__=~"debug_.*"})' -o json

# ✅ CORRECT — confirm no dashboard panel queries the metric (list has no panels; get each dashboard)
for uid in $(oodle dashboards list -o json | jq -r '.[].uid'); do
  oodle dashboards get "$uid" -o json | grep -q 'debug_traffic_total' && echo "$uid"
done

# ✅ CORRECT — confirm no monitor depends on it
oodle monitors list -o json | jq '.[] | select(.promql_query | contains("debug_traffic_total"))'

# ❌ WRONG — create the rule first, find out from on-call later
oodle drop-rules create -f rule.json
Creating a narrow rule (safer first step)
{
  "rule_name": "drop-debug-traffic-staging",
  "metric_name": {"type": 0, "name": "__name__", "value": "debug_traffic_total"},
  "filters": [
    {"type": 0, "name": "env", "value": "staging"}
  ],
  "type": "series"
}
# ✅ CORRECT — one metric in staging; observe for a week before widening
oodle drop-rules create -f rule.json
Widening a rule
# ✅ CORRECT — get → change filters → update
oodle drop-rules get dr_123 -o json > rule.json
jq '.filters = [{"type": 2, "name": "env", "value": "staging|dev"}]' rule.json > rule.new.json
oodle drop-rules update dr_123 -f rule.new.json

# ❌ WRONG — partial payload nulls metric_name and filters
oodle drop-rules update dr_123 -f <(echo '{"filters":[]}')
Deleting (re-enabling ingestion)
# ✅ CORRECT
oodle drop-rules get dr_123 -o json > /dev/null
oodle drop-rules delete dr_123 --force

# ❌ WRONG — speculative delete by name match
oodle drop-rules delete "$(oodle drop-rules list | grep debug | awk '{print $1}')" --force

Best Practices

Estimate impact with oodle metrics query --query 'count({__name__=~"<prefix>.*"})' before creating a rule

A drop rule that matches more series than expected can hide real signal.

# ✅ CORRECT
oodle metrics query --query 'count({__name__=~"kube_pod_.*"})' -o json | jq -r '.data.result[0].value[1]'
# 1742 series — confirm with the team that all 1742 are safe to drop before creating a rule

# ❌ WRONG — create rule based on a guess; later discover a critical metric was matched
oodle drop-rules create -f rule.json
Start with a narrow rule in a non-production env on the first iteration

There is no sampling mode. A narrow first rule shows that the metric truly is low-value before you drop it everywhere.

# ✅ CORRECT — week 1: drop in staging only, observe dashboards
"filters": [{"type": 0, "name": "env", "value": "staging"}]
# week 2: if no dashboards or monitors regressed, widen the filters

# ❌ WRONG — drop everywhere on first attempt; can break a dashboard nobody remembered
"filters": []
Always include both env and service (or an exact metric_name) in matchers

Broad matchers like {level: debug} alone can match production metrics that happen to share a label.

# ✅ CORRECT — scoped to one env
"filters": [{"type":0,"name":"level","value":"debug"},{"type":0,"name":"env","value":"staging"}]

# ❌ WRONG — also drops debug metrics in prod
"filters": [{"type":0,"name":"level","value":"debug"}]
Always get before update to preserve fields

Update is a full-document replace.

# ✅ CORRECT
oodle drop-rules get dr_123 -o json > rule.json
jq '.filters += [{"type": 0, "name": "service", "value": "api"}]' rule.json > rule.new.json
oodle drop-rules update dr_123 -f rule.new.json

# ❌ WRONG — drops metric_name and type
oodle drop-rules update dr_123 -f <(echo '{"filters":[{"type":0,"name":"service","value":"api"}]}')
Name rules with drop-<metric-or-domain>-<scope>

Predictable names make it easy to find and revert a rule when a dashboard breaks.

# ✅ CORRECT
"rule_name": "drop-debug-metrics-staging"
"rule_name": "drop-kube-pod-info-prod"

# ❌ WRONG
"rule_name": "rule1"

Failure Handling

ErrorCauseFix
401 UnauthorizedInvalid or missing API keyRun oodle configure or set OODLE_API_KEY
404 Not FoundDrop rule ID does not existVerify with oodle drop-rules list -o json
connection refusedWrong OODLE_DEPLOYMENT URLCheck OODLE_DEPLOYMENT env var
rule_name cannot be emptyMissing rule_nameAdd rule_name
type cannot be empty / invalid type "...", must be "series"type is missing or wrongSet "type": "series"
Dashboard panel suddenly emptyDrop rule matched a metric the panel queriesRun oodle drop-rules list -o json to find the rule; delete it (oodle drop-rules delete <id> --force) or narrow its matchers
Monitor went into no dataDrop rule matched the monitor's metricSame fix as above
Cost did not decreaseMatchers don't actually match the high-volume seriesRe-run the count(...) query with the rule's matchers and compare label sets
429 Too Many RequestsBulk drop-rule syncAdd --retries 3, throttle to <10 creates per second

References

Comments

Markdown supported