Building a Causal Attribution Engine for AI-Powered Root Cause Analysis
By
A monitoring alert can tell you, “Daily Revenue dropped 18%.” You know what happened, but you don’t know why it happened.
Traditional dashboards give you breakdowns, like revenue by region, channel, and product. But breakdowns alone can’t distinguish correlation from causation. They can't tell you whether the drop in the West region caused the revenue decline, or whether both were symptoms of a deeper issue, like an ad spend cutback three days earlier.
That gap is where a causal attribution engine becomes useful. This article focuses on the statistical attribution engine: it decomposes metric anomalies into structural signals, anomaly attribution scores, and causal chains. Those outputs are then consumed by an AI incident-investigation agent, which verifies each hypothesis with SQL, explores related dimensions, and writes the final human-readable RCA. Three questions are answered in order — Where did the delta come from? Which drivers caused it? What end-to-end story best explains it? This layered design is important because every eventual decision depends on the graph and scoring choices made up front.
The Workspace Graph
Before attribution runs, there must exist a directed acyclic graph connecting metrics. This is the workspace graph.

Nodes are metrics (UUIDs) or dimensions (dimension:region).Edges are directional — source drives target:
Compositional edges: Store Rev + Web Rev + Catalog Rev = Total Revenue
Correlational edges: Ad Spend → Txn Count (causal, possibly lagged)
At build time, all edges have weight = 0. Weights are computed live during attribution, so there are no stale pre-computed scores. Once that workspace graph exists, the pipeline can move from time-series fetch to ranked explanation.
The Attribution Pipeline
The entry point is run_full_attribution(). The 16-step flow can be read as seven larger stages. The graph and the relevant subgraph are loaded. Time series are fetched with SQL. Each node is scored for current anomaly strength. Edges are weighted with Toda-Yamamoto Granger causality, Pearson amplification, and delta alignment. Contribution and Personalized PageRank are computed. Dimension attribution is run. Finally, the output is assembled into WHERE, WHY, and STORY layers. That ordering is not cosmetic. Statistical choices made early, especially metric typing and series transforms, decide whether the causal layer will be trustworthy.

Type-Aware Recipes
Not all metrics are the same. For example, a ratio metric (Conversion Rate = Orders/Sessions) can't be decomposed the same way as an additive metric (Revenue = Σ order amounts). We classify each metric into one of 10 types and assign a recipe that controls scorer choice, transform choice, edge decomposition, dimension slicing, and drill guidance. This design keeps the engine auditable instead of turning it into a pile of ‘per-metric exceptions.’