mirror of
https://github.com/hanzo-apps/hanzo.ai.git
synced 2026-10-30 14:58:08 +00:00
The index, its boards and the shelf's pages wrap their prose: server pages with <T>, the boards and the library with t(), and copy held in data with phrase(). Figures read from the runs are values, and the fields lib/kai, lib/tools, lib/coding and lib/tally hand a board are drawn through t(), so they translate once those files emit keys. The shared parts (Chapter, Fold, Stat, Tile, Panel, Mark) translate a string where they draw it and take a node from a server page. figures.spec lets the index import @hanzo/i18n: words in, words out, never a figure.
234 lines
9.5 KiB
TypeScript
234 lines
9.5 KiB
TypeScript
/**
|
||
* /benchmarks/<slug> — one benchmark's page, for every entry of the ledger that
|
||
* has no hand-written page of its own: each Kai suite, capability, gate and
|
||
* latency run.
|
||
*
|
||
* It reads lib/results through LEDGER, so it carries what every result row
|
||
* carries and no more: the latest result beside its baseline, every run over
|
||
* time, the conditions, the hardware, the source and, where one exists, the
|
||
* command that reproduces it. The hand-written pages (gpqa, locomo, inference,
|
||
* the runtime passes, …) are static folders beside this route and win over it.
|
||
*/
|
||
import { notFound } from 'next/navigation'
|
||
import { phrase } from '@hanzo/i18n'
|
||
import { T } from '@hanzo/i18n/react'
|
||
import { pageMeta } from '@/lib/page-meta'
|
||
import { LEDGER, type Entry, type Result } from '@/lib/bench-data'
|
||
import { Eyebrow, Even, H1, H2, Inline, Lede, Meta, P, Page, Table, Td, Th, Tile, Tr } from '@/components/benchmarks/kit'
|
||
import { Mark } from '@/components/benchmarks/controls'
|
||
|
||
export const dynamicParams = false
|
||
|
||
const own = (slug: string) => LEDGER.entries.find((e) => e.slug === slug && !e.own)
|
||
export function generateStaticParams() {
|
||
return LEDGER.entries.filter((e) => !e.own).map((e) => ({ slug: e.slug }))
|
||
}
|
||
|
||
export async function generateMetadata({ params }: { params: Promise<{ slug: string }> }) {
|
||
const e = own((await params).slug)
|
||
if (!e) return {}
|
||
return pageMeta({ title: `${e.name} benchmark · ${e.product}`, description: e.what, path: `/benchmarks/${e.slug}` })
|
||
}
|
||
|
||
const STATE = { live: phrase('Live'), frozen: phrase('Frozen'), superseded: phrase('Superseded') } as const
|
||
const STANDING = { win: phrase('Win'), level: phrase('Level'), loss: phrase('Loss'), unscored: phrase('Unscored') } as const
|
||
const BY = { Hanzo: phrase('Hanzo-measured'), Vendor: phrase('vendor-reported'), Board: phrase('sealed board') } as const
|
||
|
||
/** Value over time for one metric: each dated result a point, its newest baseline a dashed line. */
|
||
function History({ rows }: { rows: Result[] }) {
|
||
const pts = rows.filter((r): r is Result & { value: number; date: string } => r.value != null && r.date != null).sort((a, b) => a.date.localeCompare(b.date))
|
||
// A history needs two days to draw; readings taken on one day are a table, not a line.
|
||
if (new Set(pts.map((p) => p.date)).size < 2) return null
|
||
const W = 720
|
||
const H = 220
|
||
const PAD = { l: 52, r: 16, t: 16, b: 32 }
|
||
const t = (d: string) => Date.parse(`${d}T00:00:00Z`)
|
||
const t0 = t(pts[0].date)
|
||
const t1 = Math.max(t(pts[pts.length - 1].date), t0 + 86_400_000)
|
||
const base = pts[pts.length - 1].base
|
||
const vs = [...pts.map((p) => p.value), ...(base != null ? [base] : [])]
|
||
const pct = vs.every((v) => v >= 0 && v <= 1)
|
||
let lo = Math.min(...vs)
|
||
let hi = Math.max(...vs)
|
||
const pad = (hi - lo || Math.abs(hi) || 1) * 0.15
|
||
lo = pct ? Math.max(0, lo - pad) : lo - pad
|
||
hi = pct ? Math.min(1, hi + pad) : hi + pad
|
||
const x = (d: string) => PAD.l + ((t(d) - t0) / (t1 - t0)) * (W - PAD.l - PAD.r)
|
||
const y = (v: number) => PAD.t + ((hi - v) / (hi - lo || 1)) * (H - PAD.t - PAD.b)
|
||
// A narrow range needs a decimal, or two ticks a point apart print the same whole number.
|
||
const fmt = (v: number) => (pct ? `${(v * 100).toFixed(hi - lo < 0.06 ? 1 : 0)}%` : v.toFixed(hi - lo < 0.06 ? 3 : 2))
|
||
const ticks = [lo, (lo + hi) / 2, hi]
|
||
const days = [...new Set(pts.map((p) => p.date))]
|
||
return (
|
||
<svg viewBox={`0 0 ${W} ${H}`} width="100%" role="img" aria-label={`${pts[0].metric} over time: ${pts.map((p) => `${p.subject} ${p.shown} on ${p.when}`).join('; ')}${base != null ? `; baseline ${pts[pts.length - 1].baseShown}` : ''}.`} display="block">
|
||
{ticks.map((v) => (
|
||
<g key={v}>
|
||
<line x1={PAD.l} x2={W - PAD.r} y1={y(v)} y2={y(v)} stroke="var(--border)" />
|
||
<text x={PAD.l - 8} y={y(v) + 4} textAnchor="end" fill="var(--muted-foreground)" fontSize={11} fontFamily="var(--font-mono, monospace)">
|
||
{fmt(v)}
|
||
</text>
|
||
</g>
|
||
))}
|
||
{days.map((d) => (
|
||
<text key={d} x={x(d)} y={H - 8} textAnchor="middle" fill="var(--muted-foreground)" fontSize={11} fontFamily="var(--font-mono, monospace)">
|
||
{d.slice(5)}
|
||
</text>
|
||
))}
|
||
{base != null ? <line x1={PAD.l} x2={W - PAD.r} y1={y(base)} y2={y(base)} stroke="var(--muted-foreground)" strokeDasharray="5 4" /> : null}
|
||
<polyline points={pts.map((p) => `${x(p.date)},${y(p.value)}`).join(' ')} fill="none" stroke="var(--text-primary)" strokeWidth={1.6} />
|
||
{pts.map((p) => (
|
||
<circle key={p.id} cx={x(p.date)} cy={y(p.value)} r={p.state === 'live' ? 6 : 4} fill={p.state === 'live' ? 'var(--text-primary)' : 'var(--background)'} stroke="var(--text-primary)" strokeWidth={1.5}>
|
||
<title>{`${p.subject}: ${p.shown}, ${p.when}`}</title>
|
||
</circle>
|
||
))}
|
||
</svg>
|
||
)
|
||
}
|
||
|
||
function Facts({ e }: { e: Entry }) {
|
||
return (
|
||
<>
|
||
<H2><T>Conditions</T></H2>
|
||
{e.conditions.length ? (
|
||
e.conditions.map((c) => (
|
||
<P key={c} render="span">
|
||
<T>{c}</T>
|
||
</P>
|
||
))
|
||
) : (
|
||
<P><T>The source records no conditions beyond the benchmark itself.</T></P>
|
||
)}
|
||
<H2><T>Hardware</T></H2>
|
||
<P>{e.hardware ?? <T>The run records no device or host.</T>}</P>
|
||
<H2><T>Source</T></H2>
|
||
<P>{e.source ? <Inline href={e.source.href}>{e.source.label}</Inline> : <T>No public record beyond this page.</T>}</P>
|
||
<H2><T>Reproduce</T></H2>
|
||
{e.command ? (
|
||
<Meta>
|
||
<code>{e.command}</code>
|
||
</Meta>
|
||
) : (
|
||
<P><T>No public command regenerates this result. The source above is the record it is read from.</T></P>
|
||
)}
|
||
</>
|
||
)
|
||
}
|
||
|
||
export default async function BenchmarkPage({ params }: { params: Promise<{ slug: string }> }) {
|
||
const e = own((await params).slug)
|
||
if (!e) notFound()
|
||
const rows = LEDGER.results.filter((r) => r.entry === e.slug).sort((a, b) => (b.date ?? '').localeCompare(a.date ?? '') || a.metric.localeCompare(b.metric))
|
||
const metrics = [...new Set(rows.map((r) => r.metric))]
|
||
const latest = metrics.flatMap((m) => rows.filter((r) => r.metric === m && r.state !== 'superseded').slice(0, m === metrics[0] ? 4 : 1))
|
||
const related = LEDGER.entries.filter((x) => x.product === e.product && x.slug !== e.slug)
|
||
return (
|
||
<Page>
|
||
<Meta>
|
||
<Inline href="/benchmarks">
|
||
<T>Benchmarks</T>
|
||
</Inline>{' '}
|
||
/ <Inline href={`/benchmarks?product=${encodeURIComponent(e.product)}#all`}>{e.product}</Inline> / {e.name}
|
||
</Meta>
|
||
<Eyebrow>
|
||
{e.product} · {e.category}
|
||
</Eyebrow>
|
||
<H1>{e.name}</H1>
|
||
<Lede>
|
||
<T>{e.what}</T>
|
||
</Lede>
|
||
|
||
{latest.length ? (
|
||
<>
|
||
<H2><T>Latest</T></H2>
|
||
<Even>
|
||
{latest.map((r) => (
|
||
<Tile
|
||
key={r.id}
|
||
figure={r.shown}
|
||
label={`${r.metric} · ${r.subject}`}
|
||
note={`${r.against ? `${r.against} ${r.baseShown ?? '–'} · ` : 'no baseline · '}${STANDING[r.standing]} · ${r.when} · ${BY[r.by]}`}
|
||
href="#history"
|
||
/>
|
||
))}
|
||
</Even>
|
||
</>
|
||
) : null}
|
||
|
||
<H2 id="history"><T>History</T></H2>
|
||
<P>
|
||
{rows.length === 1 ? (
|
||
<T>One result so far. Its history fills in as later runs are posted.</T>
|
||
) : metrics.length > 1 ? (
|
||
<T values={{ n: rows.length, m: metrics.length }}>
|
||
{"{n} results across {m} metrics, newest first. Superseded runs stay, so a revision's progress can be read."}
|
||
</T>
|
||
) : (
|
||
<T values={{ n: rows.length }}>{"{n} results, newest first. Superseded runs stay, so a revision's progress can be read."}</T>
|
||
)}
|
||
</P>
|
||
<History rows={rows.filter((r) => r.metric === metrics[0])} />
|
||
<Table>
|
||
<thead>
|
||
<tr>
|
||
<Th left><T>Measured</T></Th>
|
||
<Th left><T>Subject</T></Th>
|
||
<Th left><T>Metric</T></Th>
|
||
<Th><T>Value</T></Th>
|
||
<Th><T>Baseline</T></Th>
|
||
<Th left><T>Result</T></Th>
|
||
<Th left><T>Status</T></Th>
|
||
</tr>
|
||
</thead>
|
||
<tbody>
|
||
{rows.map((r) => (
|
||
<Tr key={r.id} dim={r.state === 'superseded'}>
|
||
<Td left>{r.when}</Td>
|
||
<Td left wrap>
|
||
{r.subject}
|
||
</Td>
|
||
<Td left wrap>
|
||
{r.metric}
|
||
</Td>
|
||
<Td>{r.shown}</Td>
|
||
<Td>{r.baseShown != null ? `${r.against ?? ''} ${r.baseShown}`.trim() : '–'}</Td>
|
||
<Td left>
|
||
<Mark s={r.standing} word={STANDING[r.standing]} />
|
||
</Td>
|
||
<Td left>
|
||
<T>{STATE[r.state]}</T> · <T>{BY[r.by]}</T>
|
||
</Td>
|
||
</Tr>
|
||
))}
|
||
</tbody>
|
||
</Table>
|
||
|
||
<Facts e={e} />
|
||
|
||
{related.length ? (
|
||
<>
|
||
<H2>
|
||
<T values={{ product: e.product }}>{'More {product} benchmarks'}</T>
|
||
</H2>
|
||
<P>
|
||
{related.map((x, i) => (
|
||
<span key={x.slug}>
|
||
{i ? ' · ' : ''}
|
||
<Inline href={x.href}>{x.name}</Inline>
|
||
</span>
|
||
))}
|
||
</P>
|
||
</>
|
||
) : null}
|
||
<Meta>
|
||
<Inline href={`/benchmarks?q=${encodeURIComponent(e.name)}#all`}>
|
||
<T values={{ name: e.name }}>{'Every result for {name} on the shelf'}</T>
|
||
</Inline>{' '}
|
||
·{' '}
|
||
<Inline href="/benchmarks#methods">
|
||
<T>How these are measured</T>
|
||
</Inline>
|
||
</Meta>
|
||
</Page>
|
||
)
|
||
}
|