Live repro on the operator's deployment, 2026-08-20. The host was down 08-14→08-20 (see the sibling outage issue). On return to service, the Moisture-history chart rendered visually empty at every range — 30d, 7d, 24h, even 1h — while the masthead counted 341,476 readings in-window and the live cards streamed normally.
Verified cause
card_context.py:1000 — the #839 Fix B "recent contiguous run" clip:
recent_start = _recent_run_start(soil, TRAJ_GAP_BOUNDARY_H) with TRAJ_GAP_BOUNDARY_H = 36.0 (card_context.py:113,904)
plot_rs = [r for r in rs if r.timestamp_utc >= recent_start]
After any ≥36h gap, the PLOT keeps only readings since the gap ended. Measured from the live endpoint: all 8 datasets contained 64–66 points, every one at x = 719.45–719.99 of a 720-hour window — the ~32 minutes since the Monitor restarted. At 30d scale that is sub-pixel at the right edge. The chart drew everything it was given; it was given 0.08% of the window.
#839's intent was right for its regime: a stale pre-gap pocket must not dominate a live view (the original bug was 0..180h of stale data bridging into the live window). Today's regime is the inversion — 24 days of good history behind the gap, 32 minutes in front of it — and the rule discards the month. The operator moment is exactly backwards: returning after an absence-shaped outage is precisely when the pre-gap history matters most, and it is precisely when this rule hides it.
This is the release family's recurring defect shape: a layer correct about the question it asks (don't bridge a hole), silent about the one nobody wired (don't discard the archive behind it).
Why the clip may no longer be needed at all
The gap-bridging harm #839 feared is already independently solved: _insert_breaks (#699, card_context.py:1376) breaks the plotted line across real dropouts post-decimation, "so the chart never interpolates a straight segment over a WiFi hole." And the fits stopped spanning gaps long ago — the trend is segment-bound (#1133) and mask-filtered (#1244 C0). The clip's remaining job description may be empty.
Candidate fix (Data's call, Design consult on the render)
Plot the full window with the #699 break across the gap (an honest visible hole, per the gaps/continuity machinery that already exists) — keep fits/trends/forecasts exactly as they are (already recent-run/segment-bound). If any clip survives, it needs a floor: never discard more than it keeps, or never clip when the pre-gap span exceeds the post-gap span.
AC:
— Workflow ⚙️ (filed from live diagnosis)
Live repro on the operator's deployment, 2026-08-20. The host was down 08-14→08-20 (see the sibling outage issue). On return to service, the Moisture-history chart rendered visually empty at every range — 30d, 7d, 24h, even 1h — while the masthead counted 341,476 readings in-window and the live cards streamed normally.
Verified cause
card_context.py:1000— the #839 Fix B "recent contiguous run" clip:recent_start = _recent_run_start(soil, TRAJ_GAP_BOUNDARY_H)withTRAJ_GAP_BOUNDARY_H = 36.0(card_context.py:113,904)plot_rs = [r for r in rs if r.timestamp_utc >= recent_start]After any ≥36h gap, the PLOT keeps only readings since the gap ended. Measured from the live endpoint: all 8 datasets contained 64–66 points, every one at x = 719.45–719.99 of a 720-hour window — the ~32 minutes since the Monitor restarted. At 30d scale that is sub-pixel at the right edge. The chart drew everything it was given; it was given 0.08% of the window.
#839's intent was right for its regime: a stale pre-gap pocket must not dominate a live view (the original bug was 0..180h of stale data bridging into the live window). Today's regime is the inversion — 24 days of good history behind the gap, 32 minutes in front of it — and the rule discards the month. The operator moment is exactly backwards: returning after an absence-shaped outage is precisely when the pre-gap history matters most, and it is precisely when this rule hides it.
This is the release family's recurring defect shape: a layer correct about the question it asks (don't bridge a hole), silent about the one nobody wired (don't discard the archive behind it).
Why the clip may no longer be needed at all
The gap-bridging harm #839 feared is already independently solved:
_insert_breaks(#699, card_context.py:1376) breaks the plotted line across real dropouts post-decimation, "so the chart never interpolates a straight segment over a WiFi hole." And the fits stopped spanning gaps long ago — the trend is segment-bound (#1133) and mask-filtered (#1244 C0). The clip's remaining job description may be empty.Candidate fix (Data's call, Design consult on the render)
Plot the full window with the #699 break across the gap (an honest visible hole, per the gaps/continuity machinery that already exists) — keep fits/trends/forecasts exactly as they are (already recent-run/segment-bound). If any clip survives, it needs a floor: never discard more than it keeps, or never clip when the pre-gap span exceeds the post-gap span.
AC:
all— Workflow ⚙️ (filed from live diagnosis)