feat: add per-ride history charts with wait time and uptime tracking
Build and Deploy / Build & Push (push) Successful in 3m7s
Build and Deploy / Build & Push (push) Successful in 3m7s
Adds a cron-driven sampler that snapshots Queue-Times waits and Six Flags Fast Lane data every 5 minutes into a new ride_wait_samples table, and a clickable per-ride detail page at /park/[id]/ride/[slug] with Today / 7d / 30d Recharts views plus a 30d uptime pill. Rides are keyed by Queue-Times' stable qt_ride_id so renames don't fragment history. Samples store pre-bucketed local_date and local_time in the park's IANA timezone so aggregations are pure SQL and DST-safe. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,41 @@
|
||||
interface Props {
|
||||
/** Mean uptime across the window, 0–1. */
|
||||
uptime: number;
|
||||
sampleCount: number;
|
||||
label: string;
|
||||
}
|
||||
|
||||
function colorFor(uptime: number): { fg: string; bg: string; border: string } {
|
||||
if (uptime >= 0.95) return { fg: "var(--color-open-text)", bg: "var(--color-open-bg)", border: "var(--color-open-border)" };
|
||||
if (uptime >= 0.8) return { fg: "var(--color-closing-text)", bg: "var(--color-closing-bg)", border: "var(--color-closing-border)" };
|
||||
return { fg: "var(--color-accent)", bg: "var(--color-accent-muted)", border: "var(--color-accent)" };
|
||||
}
|
||||
|
||||
export default function UptimePill({ uptime, sampleCount, label }: Props) {
|
||||
const { fg, bg, border } = colorFor(uptime);
|
||||
const pct = (uptime * 100).toFixed(uptime >= 0.999 ? 0 : 1);
|
||||
|
||||
return (
|
||||
<div style={{
|
||||
display: "flex",
|
||||
flexDirection: "column",
|
||||
alignItems: "flex-start",
|
||||
gap: 4,
|
||||
padding: "12px 16px",
|
||||
background: bg,
|
||||
border: `1px solid ${border}`,
|
||||
borderRadius: 8,
|
||||
minWidth: 140,
|
||||
}}>
|
||||
<span style={{ fontSize: "0.65rem", textTransform: "uppercase", letterSpacing: "0.06em", color: "var(--color-text-muted)" }}>
|
||||
{label}
|
||||
</span>
|
||||
<span style={{ fontSize: "1.5rem", fontWeight: 700, color: fg, lineHeight: 1 }}>
|
||||
{pct}%
|
||||
</span>
|
||||
<span style={{ fontSize: "0.65rem", color: "var(--color-text-dim)" }}>
|
||||
{sampleCount.toLocaleString()} sample{sampleCount === 1 ? "" : "s"}
|
||||
</span>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user