Skip to content

Commit 6aa4871

Browse files
committed
fix(renewal_rate): apply 7-day rolling mean to smooth small-denominator oscillations
On days with very few expiring sectors the per-day renewal rate swings violently between 0% and 100%. Apply a 7-day trailing rolling mean to the three per-phase rate columns so the chart shows a legible trend. Chart subtitle updated to note the smoothing.
1 parent 0ad76ef commit 6aa4871

File tree

2 files changed

+21
-2
lines changed

2 files changed

+21
-2
lines changed

datasets/renewal_rate.py

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,25 @@
6363

6464
data = client.query(sql).to_arrow(create_bqstorage_client=False)
6565

66-
df = pl.DataFrame(data).with_columns(pl.col("date").dt.strftime("%Y-%m-%d"))
66+
# Apply 7-day trailing rolling mean to the per-phase renewal rate columns to
67+
# smooth out days with very few expiry events (small denominators cause wild
68+
# 0%-100% oscillations, especially in recent data).
69+
df = (
70+
pl.DataFrame(data)
71+
.with_columns(pl.col("date").dt.strftime("%Y-%m-%d"))
72+
.sort("date")
73+
.with_columns([
74+
pl.col("renewal_rate_pre_pct")
75+
.rolling_mean(window_size=7, min_samples=1)
76+
.alias("renewal_rate_pre_pct"),
77+
pl.col("renewal_rate_during_pct")
78+
.rolling_mean(window_size=7, min_samples=1)
79+
.alias("renewal_rate_during_pct"),
80+
pl.col("renewal_rate_post_pct")
81+
.rolling_mean(window_size=7, min_samples=1)
82+
.alias("renewal_rate_post_pct"),
83+
])
84+
.sort("date", descending=True)
85+
)
6786

6887
df.write_json(f"public/{Path(__file__).stem}.json")

src/pages/index.astro

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -484,7 +484,7 @@ const renewalRateSubtitleSuffix =
484484
ys={["renewal_rate_pre_pct", "renewal_rate_during_pct", "renewal_rate_post_pct"]}
485485
labels={renewalRatePhaseLabels}
486486
title="Sector Renewal Rate by Grace-Period Phase"
487-
subtitle={`Cohort-based: renewed / (renewed + expired) by scheduled expiry date, segmented by grace window. Source: miner_sector_events.${renewalRateSubtitleSuffix}`}
487+
subtitle={`Cohort-based: renewed / (renewed + expired) by scheduled expiry date, segmented by grace window. 7-day rolling avg. Source: miner_sector_events.${renewalRateSubtitleSuffix}`}
488488
yLabel="%"
489489
/>
490490

0 commit comments

Comments
 (0)