diff --git a/src/app/benchmarks/[slug]/page.tsx b/src/app/benchmarks/[slug]/page.tsx
index eca94b4d..108c13cd 100644
--- a/src/app/benchmarks/[slug]/page.tsx
+++ b/src/app/benchmarks/[slug]/page.tsx
@@ -3,13 +3,13 @@ import { notFound } from "next/navigation";
import Link from "next/link";
import { ArrowLeft, ArrowUpRight, ChevronDown } from "lucide-react";
import {
- formatLastRun,
getBenchmark,
getBenchmarks,
getBenchmarkSlugs,
} from "@/data/benchmarks";
import { Pill } from "@/components/pill";
import { BenchmarkBody } from "@/components/benchmark-body";
+import { LiveIndicator } from "@/components/live-indicator";
import { SectionLabel } from "@/components/summary-stat";
import { CATEGORY_COLOR } from "@/lib/category-colors";
import { SITE } from "@/data/site";
@@ -123,14 +123,16 @@ export default async function BenchmarkPage({
{/* Bench identifier — minimal mono line, no SaaS-style pills. */}
-
+
{benchmark.category}
{isDraft && draft}
-
- Updated {formatLastRun(benchmark.lastRunAt)}
-
+ {!isDraft && (
+
+
+
+ )}
{/* Title */}
diff --git a/src/components/benchmark-body.tsx b/src/components/benchmark-body.tsx
index dc08675d..7bc0c0f5 100644
--- a/src/components/benchmark-body.tsx
+++ b/src/components/benchmark-body.tsx
@@ -56,11 +56,21 @@ export function BenchmarkBody({
return (
<>
- {options.length > 0 && (
-
+
+ {options.length > 0 ? (
-
- )}
+ ) : (
+
+ )}
+ {!isDraft && (
+
+ )}
+
{!isDraft && benchmark.unit === "count" && (
<>
@@ -69,14 +79,6 @@ export function BenchmarkBody({
Provider ledger
-
-
-
>
)}
@@ -112,7 +114,6 @@ export function BenchmarkBody({
- {benchmark.metric} · last 24 hours
{benchmark.results.length >= 5 || benchmark.unit === "bps" ? (
) : (
@@ -131,15 +132,6 @@ export function BenchmarkBody({
)}
-
-
-
-
>
)}
>
diff --git a/src/components/live-dot.tsx b/src/components/live-dot.tsx
new file mode 100644
index 00000000..7ec74e85
--- /dev/null
+++ b/src/components/live-dot.tsx
@@ -0,0 +1,16 @@
+/**
+ * Tiny pulsing green dot used inline in section labels to signal that
+ * the surrounding figure reflects live data. Discreet by design — when
+ * paired with the masthead `LiveIndicator`, this is just visual reinforcement.
+ */
+export function LiveDot({ className = "" }: { className?: string }) {
+ return (
+
+
+
+
+ );
+}
diff --git a/src/components/live-indicator.tsx b/src/components/live-indicator.tsx
new file mode 100644
index 00000000..19c5fd1a
--- /dev/null
+++ b/src/components/live-indicator.tsx
@@ -0,0 +1,53 @@
+"use client";
+
+import { useEffect, useState } from "react";
+
+/**
+ * Real-time freshness indicator for a bench: a pulsing green dot plus a
+ * "Live · updated Ns ago" counter that ticks client-side every second.
+ * Falls back to a muted "Stale" state if `lastRunAt` is older than 5 min,
+ * which usually means the harness is down or ISR is wedged — better to
+ * show staleness than to lie about freshness.
+ */
+export function LiveIndicator({ lastRunAt }: { lastRunAt: string }) {
+ const [now, setNow] = useState(() => Date.now());
+
+ useEffect(() => {
+ const id = setInterval(() => setNow(Date.now()), 1000);
+ return () => clearInterval(id);
+ }, []);
+
+ const ageSec = Math.max(0, Math.floor((now - new Date(lastRunAt).getTime()) / 1000));
+ const stale = ageSec > 300;
+
+ return (
+
+
+ {!stale && (
+
+ )}
+
+
+
+ {stale ? "Stale" : "Live"}
+
+ ·
+ updated {formatAge(ageSec)} ago
+
+ );
+}
+
+function formatAge(sec: number): string {
+ if (sec < 60) return `${sec}s`;
+ const min = Math.floor(sec / 60);
+ if (min < 60) return `${min}m`;
+ const h = Math.floor(min / 60);
+ if (h < 24) return `${h}h`;
+ return `${Math.floor(h / 24)}d`;
+}
diff --git a/src/components/ranked-bar-chart.tsx b/src/components/ranked-bar-chart.tsx
index 5f96812e..c75e8cef 100644
--- a/src/components/ranked-bar-chart.tsx
+++ b/src/components/ranked-bar-chart.tsx
@@ -4,6 +4,7 @@ import { useMemo } from "react";
import type { Benchmark } from "@/types/benchmark";
import { fmtUnit } from "@/lib/format";
import { buildProviderColors } from "@/lib/series-colors";
+import { LiveDot } from "@/components/live-dot";
type Props = { benchmark: Benchmark };
@@ -45,6 +46,10 @@ export function RankedBarChart({ benchmark }: Props) {
return (
+
+
+ {benchmark.metric} · last 24 hours
+
{rows.map((r, idx) => {
const w = project(r.value);
diff --git a/src/components/share-section.tsx b/src/components/share-section.tsx
index 37fa8e6e..550decd6 100644
--- a/src/components/share-section.tsx
+++ b/src/components/share-section.tsx
@@ -173,7 +173,7 @@ export function ShareSection({ slug, title, benchmark, chain }: Props) {
<>