refactor(kpi): K13/K15 trend review fixups — per-metric isolation, disable-during-load + logging, loading-flag finally, test coverage

This commit is contained in:
Joseph Doherty
2026-06-17 20:44:34 -04:00
parent 7d7c6cbb05
commit eb4bce3e49
7 changed files with 151 additions and 55 deletions
@@ -237,10 +237,13 @@ public class HealthPageTests : BunitContext
Assert.Contains("data-test=\"site-health-trends\"", cut.Markup);
Assert.Contains("data-test=\"site-health-trends-site\"", cut.Markup);
// The four metric charts render (the shared KpiTrendChart slug hook),
// and the seeded non-empty series draws a polyline.
// and the seeded non-empty series draws a polyline. The "S&F Buffer
// Depth" title slugifies to "s-f-buffer-depth" (the & and the spaces
// each collapse to a dash) — see KpiTrendChart.Slugify.
Assert.Contains("kpi-trend-connections-down", cut.Markup);
Assert.Contains("kpi-trend-dead-letters", cut.Markup);
Assert.Contains("kpi-trend-script-errors", cut.Markup);
Assert.Contains("kpi-trend-s-f-buffer-depth", cut.Markup);
Assert.Contains("<polyline", cut.Markup);
});
}
@@ -178,6 +178,44 @@ public class NotificationKpisPageTests : BunitContext
});
}
[Fact]
public void PartialTrendFailure_IsolatesToTheFailingMetric()
{
// Per-metric isolation (K13 fixup): the substitute returns a known series
// for two metrics but THROWS for "parkedCount". The two surviving charts
// must still draw their polylines while only the failing chart degrades to
// the unavailable placeholder — one metric's failure no longer blanks all
// three (and does not discard the already-fetched siblings).
_kpiHistory.GetSeriesAsync(
Arg.Any<string>(), Arg.Is<string>(m => m == "parkedCount"), Arg.Any<string>(),
Arg.Any<string?>(), Arg.Any<DateTime>(), Arg.Any<DateTime>(),
Arg.Any<int?>(), Arg.Any<CancellationToken>())
.Returns<Task<IReadOnlyList<KpiSeriesPoint>>>(_ => throw new InvalidOperationException("parked metric down"));
var cut = Render<NotificationKpisPage>();
cut.WaitForAssertion(() =>
{
// The page is still alive — KPI tiles render and the trends section
// never went fully blank.
Assert.Contains("Queue Depth", cut.Markup);
Assert.NotNull(cut.Find("[data-test=\"notification-trends\"]"));
// The two surviving metrics (queueDepth, deliveredLastInterval) drew
// their polylines …
var queueChart = cut.Find("[data-test=\"kpi-trend-queue-depth\"]");
Assert.Contains("<polyline", queueChart.InnerHtml);
var deliveredChart = cut.Find("[data-test=\"kpi-trend-delivered-interval\"]");
Assert.Contains("<polyline", deliveredChart.InnerHtml);
// … while only the failing "Parked" chart degraded to the unavailable
// placeholder (no polyline, the short error message instead).
var parkedChart = cut.Find("[data-test=\"kpi-trend-parked\"]");
Assert.DoesNotContain("<polyline", parkedChart.InnerHtml);
Assert.Contains("Trend data unavailable.", parkedChart.InnerHtml);
});
}
[Fact]
public void TrendQueryFailure_DoesNotBreakPage()
{