Guard rate/percentage calculations against zero denominators to prevent NaN from poisoning downstream metrics and serialization.
Rate and percentage metrics (errorRate, successRate, cacheHitRatio, …) must check for a zero denominator before dividing.
In Java, integer x/0 throws; double x/0.0 yields NaN or ±Infinity. NaN then propagates silently through sum, avg, and other aggregates, corrupting downstream metrics, and serializes as "NaN" in JSON — which many clients reject outright. The bug usually surfaces only when a new or idle tenant has zero traffic in a bucket, so early tests miss it.
double errorRate = (servicedCount != 0)
? ((double) errorCount / servicedCount) * 100.0
: 0.0;
Helper form:
static double safeRate(long num, long den) {
return den == 0 ? 0.0 : (double) num / den;
}
NaN, guard at the source, not just at the last division.0.0 is a choice. For some metrics null is more honest: "no data" ≠ "0%". Pick per metric, and document in the DTO comment.NaN element can poison a reduce/collect — guard at the producer, not only at the consumer.NaN — one guard doesn't protect the chain.