All insights

Engineering

Observability for Production ML: Catching Model Decay Before Your Users Do

Standard observability tells you the service is up. It says nothing about whether the model is still right. Data drift, concept drift, and silent degradation need their own instrumentation. Here is the stack that works.

Root Digit Platform · ML Platform Engineering6 min read

Software monitoring answers whether the system is running. Machine learning monitoring must answer whether it is still right, and those are different questions with different failure signatures. A model that has silently degraded to below-baseline accuracy emits no errors, serves every request within its latency SLO, and shows a perfectly healthy dashboard.

Three kinds of drift, with different causes and different remedies

Conflating them leads to the wrong intervention. The distinction is in which part of the joint distribution moved.

TypeWhat movedExampleResponse
Covariate shiftP(X)New customer segment, new sensorRetrain, or reweight to source
Label shiftP(Y)Fraud base rate risesRecalibrate threshold, adjust prior
Concept driftP(Y|X)Fraud tactics change; same features, new meaningRetrain on recent labels; possibly re-feature
Retraining fixes the first two. It does not fix the third if the features no longer carry the signal — a concept drift may require new features or a different problem formulation entirely.

Only covariate shift is detectable from inputs alone, which is precisely why it dominates monitoring tooling — it is the cheap one to observe. Concept drift is the dangerous one and it is invisible without labels, because the inputs can look entirely normal while their relationship to the outcome has inverted.

Measuring input drift without generating an alarm every day

Population Stability Index is the industry standard for univariate drift, largely because its thresholds have survived decades of use in credit risk and are broadly understood by the people who must act on them.

PSI  =  ∑i=1B   ( ai − ei )  ·  ln( ai / ei )

a_i — actual proportion in bin i · e_i — expected proportion from the reference window. Convention: < 0.1 stable, 0.1–0.25 moderate shift, > 0.25 significant. Symmetric in its arguments, unlike KL divergence.

Alternatives suit different data. Kolmogorov-Smirnov is distribution-free for continuous features and gives a p-value, which is convenient and also a trap. Wasserstein distance respects the ordering of values, so it distinguishes a small shift from a large one rather than only reporting that a difference exists — usually preferable for numeric features where magnitude matters.

Univariate tests also miss the drift that matters most. Two features can each retain their marginal distribution while their correlation inverts — every univariate test passes and the joint distribution the model learned no longer exists. The practical multivariate detector is a domain classifier: train a discriminator to distinguish reference-window data from current data. If it cannot beat chance, the distributions are similar. If it achieves high AUC, they are not, and its feature importances say where the difference is.

drift  ≈  2 · AUCref vs current  −  1

AUC ≈ 0.5 means indistinguishable; approaching 1.0 means trivially separable, and the classifier's own importances identify the responsible features. Simple, multivariate, and interpretable.

The label lag problem, and estimating performance without labels

Ground truth arrives late or not at all. A credit default is known in months, a churn label after the contract period, a maintenance prediction only when the asset fails or does not. During that window the model is making decisions and its accuracy is unmeasurable by direct means.

Performance can still be estimated. Under covariate shift alone — the assumption that P(Y|X) is unchanged — the model's own calibrated confidence carries usable information about the accuracy it is achieving on the current input distribution.

𝔼[ accuracy ]  ≈  (1/n)   ∑j=1n   maxc   p̂( c  |  xj )

Valid only for a well-calibrated model under covariate shift, and it cannot detect concept drift by construction — the assumption it rests on is exactly what concept drift violates. Calibration must be verified, not assumed.

Alongside this, monitor proxies available immediately: prediction distribution against its historical shape, the rate of low-confidence predictions, the fraction of inputs falling outside the training distribution, and downstream operational signals — override rate, manual review volume, customer complaint rate. None is a substitute for accuracy. Together they detect most degradation well before labels arrive.

Attribution drift catches what score drift misses

A subtle and common failure: the output distribution stays stable while the reasoning behind it changes completely. Aggregate scores look fine because two shifts offset, while the model has begun relying on a feature that recently became unreliable — a data pipeline silently defaulting a field to zero, for instance.

Tracking mean absolute attribution per feature over time surfaces this directly. A feature whose contribution doubles in a week did not become more predictive; something upstream changed. This detects broken feature pipelines faster than any output-side metric, and broken pipelines are more common in production than genuine distributional change.

Training-serving skew: the bug that monitoring exists to catch

The most frequent cause of a model performing worse in production than in evaluation is not drift at all. It is that the features computed at serving time differ from those computed at training time — a different library version, a timezone assumption, a null handled differently, an aggregation window off by an hour.

The structural fix is a feature store that computes each feature once, with the same code path serving training and inference. Where that is not available, the detective control is to log serving-time features and periodically recompute the training-time values for the same entities and compare. Any non-zero divergence is a defect, and finding it this way takes hours rather than the weeks it takes to find it by investigating unexplained accuracy loss.

What to alert on

  • Aggregate multivariate drift crossing threshold — one alert, not two hundred.
  • Estimated performance falling below the business floor, with the floor derived from the cost model rather than picked.
  • Prediction distribution shifting beyond its historical envelope.
  • Feature attribution moving sharply — almost always an upstream defect.
  • Serving-training feature divergence — any non-zero value is actionable.
  • Actual performance when labels land, as the ground truth that validates every estimate above.

And define the response before the alert fires. An alert with no agreed action becomes noise within a month, and the models that survive longest in production are the ones where drift detection is wired to a retraining pipeline that a human approves rather than to a dashboard that a human is supposed to notice.

Explore how Root Digit can support your team

From discovery workshops to production deployment, our engineers and consultants partner with you across the lifecycle of your AI, robotics, and IoT initiatives.

Cookie Policy

We use cookies to enhance your browsing experience, serve personalized content, and analyze our traffic. By clicking "Accept All", you consent to our use of cookies. You can also choose "Necessary Only" to limit cookies to essential website functions only. Learn more