Skip to content

Metric overlay

Step 3 of the three-step cross-pillar flow. Returns two timeseries (anchor + candidate) pre-aligned to the same timestamp grid, plus deterministic facts: peak_anchor_at, peak_candidate_at, peak_offset_seconds (negative = candidate leads anchor), and n_buckets_aligned.

No Pearson, no tier, no verdict. The agent reads the aligned series the same way an SRE opens two Grafana panels side by side.

Example

You

overlay apm_request_duration_p99 against Payment_Gateway_Timeout

Log10x

Overlay: peak_offset_seconds=−60 (candidate leads anchor by 60s) · 42 aligned buckets.

The p99 latency spike at 14:03 preceded the pattern volume spike at 14:04.

Prerequisites

LOG10X_CUSTOMER_METRICS_URL configured. Reporter deployed for log10x pattern anchors.

Schema and samples

Input schema

Agent-facing JSON Schema (the canonical shape the MCP server publishes via tools/list):

{
  "type": "object",
  "properties": {
    "anchor_type": {
      "type": "string",
      "enum": [
        "log10x_pattern",
        "customer_metric"
      ],
      "description": "Which side the anchor comes from. `log10x_pattern`: anchor is a 10x pattern symbol_message. `customer_metric`: anchor is a customer PromQL expression."
    },
    "anchor": {
      "type": "string",
      "description": "The anchor identity. For `log10x_pattern`: the pattern symbol_message (e.g. `error_processing_payment_$`). For `customer_metric`: a PromQL expression (e.g. `apm_request_duration_p99{service=\"payments\"}`)."
    },
    "candidate": {
      "type": "string",
      "description": "The candidate metric to overlay against the anchor. Must be a customer-side PromQL expression that returns a single series. Alias of `candidates[0]` — pass either form (sibling tools metrics_that_moved and rank_by_shape_similarity use `candidates` array; this tool accepts both for consistency)."
    },
    "candidates": {
      "type": "array",
      "items": {
        "type": "string"
      },
      "minItems": 1,
      "description": "Candidates array. Accepted for parity with metrics_that_moved + rank_by_shape_similarity. Only the first element is overlaid (metric_overlay is single-candidate by design — use rank_by_shape_similarity to rank N first, then overlay the winner)."
    },
    "window": {
      "type": "string",
      "default": "1h",
      "description": "Time window. PromQL-style duration: `15m`, `1h`, `6h`, `24h`. Alias: `timeRange`."
    },
    "timeRange": {
      "type": "string",
      "description": "Alias for `window`."
    },
    "step": {
      "type": "string",
      "default": "30s",
      "description": "Bucket step. Smaller = more samples + more cost. Default 30s."
    },
    "max_buckets": {
      "type": "number",
      "minimum": 20,
      "maximum": 2000,
      "default": 240,
      "description": "Max buckets to return in the aligned output. Pre-truncates from the most recent end if window/step exceeds this."
    },
    "environment": {
      "type": "string",
      "description": "Environment nickname (for multi-env setups)."
    }
  },
  "required": [
    "anchor_type",
    "anchor"
  ],
  "additionalProperties": false
}

Source: src/tools/metric-overlay.ts.

Output schema

The data block inside the StructuredOutput envelope:

interface ToolData {
  series: Array<{ ts: number; anchor_value: number; candidate_value: number }>;
  peak_anchor_at: number;
  peak_anchor_value: number;
  peak_candidate_at: number;
  peak_candidate_value: number;
  peak_offset_seconds: number;
  n_buckets_aligned: number;
}

Envelope-level fields: summary.headline, actions[], schema_epoch.