Anka commited on
Commit
f737def
·
1 Parent(s): 2355bb3

Add Help: intro tour, tutorials, stakeholder guides, citation info, footer

Browse files
.gitignore CHANGED
@@ -57,3 +57,5 @@ docs/INTERPRETIVE_SIGNALS.md
57
  # Playwright e2e output (tests/e2e via @playwright/test)
58
  test-results/
59
  playwright-report/
 
 
 
57
  # Playwright e2e output (tests/e2e via @playwright/test)
58
  test-results/
59
  playwright-report/
60
+
61
+ public/tutorials/screenshots/
app/about/page.tsx CHANGED
@@ -1,6 +1,7 @@
1
  import Link from "next/link"
2
- import { ArrowRight } from "lucide-react"
3
 
 
4
  import { Navigation } from "@/components/navigation"
5
 
6
  export default function AboutPage() {
@@ -116,41 +117,57 @@ export default function AboutPage() {
116
  </section>
117
 
118
  {/* FOUR SIGNALS --------------------------------------------------- */}
119
- <section className="mb-14">
120
  <div className="section-head">
121
  <h2>Four interpretive signals</h2>
122
  </div>
123
- <p className="mb-5 max-w-[700px] text-[15px] leading-[1.7] text-[color:var(--fg-muted)]">
124
- Computed over each <code className="font-mono text-[12px]">(model, benchmark, metric-path)</code> record and aggregated to the
125
- corpus. Per-record instances appear on every model and benchmark page;
126
- corpus rollups appear on the home page.
 
 
 
 
 
 
 
 
127
  </p>
128
  <ol className="list-none p-0 m-0">
129
  {[
130
- [
131
- "reproducibility",
132
- "Reproducibility",
133
- "Can a third party run this evaluation and obtain a comparable number? Tracks setup-variant disclosure, prompt and decoding parameters, harness version, seed, and code/artifact availability.",
134
- ],
135
- [
136
- "completeness",
137
- "Completeness",
138
- "Does the record meet the standard report card for this class of model? Tracks coverage across capability, robustness, safety and fairness benchmarks expected for the model's claimed use.",
139
- ],
140
- [
141
- "provenance",
142
- "Provenance & risk",
143
- "Who produced this number, and which deployment-relevant property does it speak to? Tracks evaluator identity (first-party / third-party), source citation, and IBM Risk Atlas-aligned risk domain.",
144
- ],
145
- [
146
- "comparability",
147
- "Comparability",
148
- "Can two scores under the same benchmark be put side-by-side? Tracks slice, metric variant, and unit harmonisation; flags rows that cannot be ranked together.",
149
- ],
150
- ].map(([id, h, p], i) => (
 
 
 
 
 
 
 
 
151
  <li
152
- key={h}
153
- id={`signal-${id}`}
154
  className="grid grid-cols-[50px_1fr] gap-5 border-b border-[color:var(--border-soft)] py-5 scroll-mt-24"
155
  >
156
  <span
@@ -164,14 +181,28 @@ export default function AboutPage() {
164
  0{i + 1}
165
  </span>
166
  <div>
167
- <h3 className="m-0 text-[17px] font-semibold text-[color:var(--fg)]">{h}</h3>
168
- <p className="mt-1.5 m-0 text-sm leading-[1.65] text-[color:var(--fg-muted)]">
169
- {p}
 
 
 
 
 
 
 
 
170
  </p>
171
  </div>
172
  </li>
173
  ))}
174
  </ol>
 
 
 
 
 
 
175
  </section>
176
 
177
  {/* READER MODES --------------------------------------------------- */}
@@ -337,28 +368,12 @@ export default function AboutPage() {
337
  </ul>
338
  </section>
339
 
340
- {/* CITATION & CORRECTIONS ----------------------------------------- */}
341
- <section className="mb-8">
342
  <div className="section-head">
343
- <h2>Citation &amp; corrections</h2>
344
- </div>
345
- <div className="grid gap-5 sm:grid-cols-2">
346
- <div className="border border-[color:var(--border-soft)] p-[22px]">
347
- <div className="kicker mb-2.5">Cite as</div>
348
- <p className="font-mono m-0 text-[12px] leading-[1.7] text-[color:var(--fg)]">
349
- EvalEval Coalition. (2026). Evaluation Cards: a reporting layer for AI evaluation
350
- (snapshot 5 Jun 2026). evalcards.evalevalai.com
351
- </p>
352
- </div>
353
- <div className="border border-[color:var(--border-soft)] p-[22px]">
354
- <div className="kicker mb-2.5">Submit a correction</div>
355
- <p className="m-0 text-[13.5px] leading-[1.65] text-[color:var(--fg-muted)]">
356
- Each record links a correction path. Disclosure gaps close as developers and
357
- third parties publish; we accept patches against any (model, benchmark,
358
- metric-path) tuple with a citation.
359
- </p>
360
- </div>
361
  </div>
 
362
  </section>
363
 
364
  {/* CTA ROW -------------------------------------------------------- */}
@@ -373,6 +388,10 @@ export default function AboutPage() {
373
  <Link href="/evals" className="btn-ec outline">
374
  Browse evaluations
375
  </Link>
 
 
 
 
376
  </section>
377
  </main>
378
  </div>
 
1
  import Link from "next/link"
2
+ import { ArrowRight, ExternalLink } from "lucide-react"
3
 
4
+ import { CiteSection, PAPER_URL } from "@/components/cite-section"
5
  import { Navigation } from "@/components/navigation"
6
 
7
  export default function AboutPage() {
 
117
  </section>
118
 
119
  {/* FOUR SIGNALS --------------------------------------------------- */}
120
+ <section id="four-interpretive-signals" className="mb-14 scroll-mt-24">
121
  <div className="section-head">
122
  <h2>Four interpretive signals</h2>
123
  </div>
124
+ <p className="mb-5 max-w-[720px] text-[15px] leading-[1.7] text-[color:var(--fg-muted)]">
125
+ The four signals come from a question that kept coming up in our interviews with
126
+ researchers and policy practitioners: do I have enough information to trust this
127
+ result as a basis for a decision? Each one answers a different part of it. They're
128
+ computed for every{" "}
129
+ <code className="font-mono text-[12px]">(model, benchmark, metric-path)</code> record
130
+ and rolled up across the corpus — you'll see them on each model and benchmark page,
131
+ and the corpus-wide picture on the home page. For the exact formulas, see the{" "}
132
+ <Link href="/help/how-signals-are-computed" className="underline underline-offset-2">
133
+ signal computation reference
134
+ </Link>
135
+ .
136
  </p>
137
  <ol className="list-none p-0 m-0">
138
  {[
139
+ {
140
+ id: "reproducibility",
141
+ name: "Reproducibility",
142
+ question: "Could someone else re-run this and get the same number?",
143
+ body: "We check for the small set of fields you'd need to reproduce a run — temperature and max tokens, plus the harness, evaluation plan, and limits for agentic evaluations. If any are missing, the result is flagged and the specific missing fields are listed.",
144
+ meta: "Per (model, benchmark, metric-path) · flag + missing-field list",
145
+ },
146
+ {
147
+ id: "completeness",
148
+ name: "Reporting completeness",
149
+ question: "Is the score documented well enough to interpret?",
150
+ body: "This looks at the full 28-field schema around a benchmark — its goals, construct definitions, scoring rubric, intended uses, and known limitations — not just the handful of fields needed to re-run it. Present fields score 1, fields with sub-items score the fraction filled in, and the completeness score is the average. It measures how much is documented, not how rigorous the work was.",
151
+ meta: "Per benchmark · score 0–1 + missing-field count",
152
+ },
153
+ {
154
+ id: "provenance",
155
+ name: "Provenance & risk",
156
+ question: "Who reported it, and what's at stake?",
157
+ body: "For each score we surface who ran it the model developer (first-party), an independent evaluator (third-party), or a collaboration — and whether more than one party reported the same thing. We also carry over any risk categories tied to the benchmark, drawn from the Auto-BenchmarkCards risk mapping. First- and third-party results are never quietly merged.",
158
+ meta: "Per (model, benchmark, metric-path) · party tag + multi-party flag + risk tags",
159
+ },
160
+ {
161
+ id: "comparability",
162
+ name: "Comparability",
163
+ question: "Can these scores actually be compared?",
164
+ body: "When the same model, benchmark, and metric has more than one reported score, we check whether they differ by more than 5% of the metric's range — both across different setups from the same party (variant divergence) and across different parties (cross-party divergence). If they diverge, we flag it and show the setup differences behind the gap.",
165
+ meta: "Per (model, benchmark, metric-path), ≥2 reports · variant + cross-party divergence flags",
166
+ },
167
+ ].map((s, i) => (
168
  <li
169
+ key={s.id}
170
+ id={`signal-${s.id}`}
171
  className="grid grid-cols-[50px_1fr] gap-5 border-b border-[color:var(--border-soft)] py-5 scroll-mt-24"
172
  >
173
  <span
 
181
  0{i + 1}
182
  </span>
183
  <div>
184
+ <h3 className="m-0 text-[17px] font-semibold text-[color:var(--fg)]">
185
+ {s.name}
186
+ </h3>
187
+ <p className="mt-0.5 m-0 text-[13.5px] italic leading-[1.5] text-[color:var(--fg-subtle)]">
188
+ {s.question}
189
+ </p>
190
+ <p className="mt-2 m-0 text-sm leading-[1.65] text-[color:var(--fg-muted)]">
191
+ {s.body}
192
+ </p>
193
+ <p className="mt-2.5 m-0 font-mono text-[11px] uppercase tracking-[0.08em] text-[color:var(--fg-subtle)]">
194
+ {s.meta}
195
  </p>
196
  </div>
197
  </li>
198
  ))}
199
  </ol>
200
+ <p className="mt-5 max-w-[720px] text-sm leading-[1.7] text-[color:var(--fg-muted)]">
201
+ None of this is a grade. Evaluation Cards doesn't hand out letter grades, pass/fail
202
+ thresholds, or rankings — it just makes reporting choices visible. A missing field
203
+ lowers a completeness score and may trip another signal, and we show readers exactly
204
+ what was left out.
205
+ </p>
206
  </section>
207
 
208
  {/* READER MODES --------------------------------------------------- */}
 
368
  </ul>
369
  </section>
370
 
371
+ {/* HOW TO CITE ---------------------------------------------------- */}
372
+ <section id="how-to-cite" className="mb-8 scroll-mt-24">
373
  <div className="section-head">
374
+ <h2>How to cite</h2>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
375
  </div>
376
+ <CiteSection showCorrection />
377
  </section>
378
 
379
  {/* CTA ROW -------------------------------------------------------- */}
 
388
  <Link href="/evals" className="btn-ec outline">
389
  Browse evaluations
390
  </Link>
391
+ <a href={PAPER_URL} target="_blank" rel="noreferrer" className="btn-ec outline">
392
+ Read the paper
393
+ <ExternalLink className="h-3.5 w-3.5" aria-hidden />
394
+ </a>
395
  </section>
396
  </main>
397
  </div>
app/globals.css CHANGED
@@ -1485,3 +1485,149 @@
1485
  transition: none;
1486
  }
1487
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1485
  transition: none;
1486
  }
1487
  }
1488
+
1489
+ /* ---------------------------------------------------------------------------
1490
+ Tutorial prose — rendered markdown for /help guides. Scoped so it can't
1491
+ leak into the rest of the app; uses the same design tokens as the site.
1492
+ --------------------------------------------------------------------------- */
1493
+ .tutorial-prose {
1494
+ color: var(--fg);
1495
+ font-size: 16px;
1496
+ line-height: 1.7;
1497
+ }
1498
+ .tutorial-prose > :first-child {
1499
+ margin-top: 0;
1500
+ }
1501
+ .tutorial-prose h1 {
1502
+ font-size: clamp(32px, 4.4vw, 44px);
1503
+ font-weight: 700;
1504
+ letter-spacing: -0.03em;
1505
+ line-height: 1.08;
1506
+ margin: 0 0 0.5em;
1507
+ color: var(--fg);
1508
+ }
1509
+ .tutorial-prose h2 {
1510
+ font-size: 24px;
1511
+ font-weight: 650;
1512
+ letter-spacing: -0.015em;
1513
+ margin: 2em 0 0.6em;
1514
+ padding-bottom: 0.3em;
1515
+ border-bottom: 1px solid var(--border-soft);
1516
+ color: var(--fg);
1517
+ }
1518
+ .tutorial-prose h3 {
1519
+ font-size: 18px;
1520
+ font-weight: 600;
1521
+ margin: 1.6em 0 0.4em;
1522
+ color: var(--fg);
1523
+ }
1524
+ .tutorial-prose p {
1525
+ margin: 0 0 1.1em;
1526
+ color: var(--fg-muted);
1527
+ }
1528
+ .tutorial-prose strong {
1529
+ color: var(--fg);
1530
+ font-weight: 600;
1531
+ }
1532
+ .tutorial-prose a {
1533
+ color: var(--fg);
1534
+ text-decoration: underline;
1535
+ text-underline-offset: 2px;
1536
+ text-decoration-color: var(--border-strong);
1537
+ }
1538
+ .tutorial-prose a:hover {
1539
+ text-decoration-color: var(--accent);
1540
+ }
1541
+ .tutorial-prose ul,
1542
+ .tutorial-prose ol {
1543
+ margin: 0 0 1.1em;
1544
+ padding-left: 1.4em;
1545
+ color: var(--fg-muted);
1546
+ }
1547
+ .tutorial-prose li {
1548
+ margin: 0.3em 0;
1549
+ }
1550
+ .tutorial-prose li::marker {
1551
+ color: var(--fg-subtle);
1552
+ }
1553
+ .tutorial-prose code {
1554
+ font-family: var(--font-mono, ui-monospace, monospace);
1555
+ font-size: 0.86em;
1556
+ background: var(--bg-subtle);
1557
+ border: 1px solid var(--border-soft);
1558
+ border-radius: 3px;
1559
+ padding: 0.1em 0.35em;
1560
+ color: var(--fg);
1561
+ }
1562
+ .tutorial-prose pre {
1563
+ background: var(--bg-subtle);
1564
+ border: 1px solid var(--border-soft);
1565
+ border-radius: var(--radius);
1566
+ padding: 1em 1.2em;
1567
+ overflow-x: auto;
1568
+ margin: 0 0 1.4em;
1569
+ }
1570
+ .tutorial-prose pre code {
1571
+ background: none;
1572
+ border: none;
1573
+ padding: 0;
1574
+ font-size: 13px;
1575
+ }
1576
+ .tutorial-prose blockquote {
1577
+ margin: 0 0 1.4em;
1578
+ padding: 0.2em 0 0.2em 1.1em;
1579
+ border-left: 3px solid var(--border-strong);
1580
+ color: var(--fg-muted);
1581
+ }
1582
+ .tutorial-prose blockquote p {
1583
+ margin: 0.3em 0;
1584
+ }
1585
+ .tutorial-prose hr {
1586
+ border: none;
1587
+ border-top: 1px solid var(--border-soft);
1588
+ margin: 2.2em 0;
1589
+ }
1590
+ .tutorial-prose table {
1591
+ width: 100%;
1592
+ border-collapse: collapse;
1593
+ margin: 0 0 1.6em;
1594
+ font-size: 14px;
1595
+ }
1596
+ .tutorial-prose th,
1597
+ .tutorial-prose td {
1598
+ border: 1px solid var(--border-soft);
1599
+ padding: 0.6em 0.8em;
1600
+ text-align: left;
1601
+ vertical-align: top;
1602
+ }
1603
+ .tutorial-prose th {
1604
+ background: var(--bg-warm);
1605
+ font-weight: 600;
1606
+ color: var(--fg);
1607
+ }
1608
+ .tutorial-prose td {
1609
+ color: var(--fg-muted);
1610
+ }
1611
+ .tutorial-prose .tut-figure {
1612
+ margin: 1.8em 0;
1613
+ }
1614
+ /* Cap height so very tall full-page captures scroll inside a frame rather than
1615
+ stretching the page; normal section crops fall well under this. */
1616
+ .tutorial-prose .tut-figure-frame {
1617
+ max-height: 560px;
1618
+ overflow: auto;
1619
+ border: 1px solid var(--border-soft);
1620
+ border-radius: var(--radius);
1621
+ background: var(--bg-subtle);
1622
+ }
1623
+ .tutorial-prose .tut-figure img {
1624
+ width: 100%;
1625
+ height: auto;
1626
+ display: block;
1627
+ }
1628
+ .tutorial-prose .tut-figure figcaption {
1629
+ margin-top: 0.6em;
1630
+ font-size: 13px;
1631
+ line-height: 1.5;
1632
+ color: var(--fg-subtle);
1633
+ }
app/help/[slug]/page.tsx ADDED
@@ -0,0 +1,68 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import Link from "next/link"
2
+ import type { Metadata } from "next"
3
+ import { notFound } from "next/navigation"
4
+ import { ArrowLeft } from "lucide-react"
5
+ import "katex/dist/katex.min.css"
6
+
7
+ import { Navigation } from "@/components/navigation"
8
+ import { ReplayIntroButton } from "@/components/replay-intro-button"
9
+ import { TutorialMarkdown } from "@/components/tutorial-markdown"
10
+ import { getTutorialMeta, getTutorialSlugs, readTutorial } from "@/lib/tutorials"
11
+
12
+ export function generateStaticParams() {
13
+ return getTutorialSlugs().map((slug) => ({ slug }))
14
+ }
15
+
16
+ export async function generateMetadata({
17
+ params,
18
+ }: {
19
+ params: Promise<{ slug: string }>
20
+ }): Promise<Metadata> {
21
+ const { slug } = await params
22
+ const meta = getTutorialMeta(slug)
23
+ if (!meta) return {}
24
+ return { title: `${meta.title} · Help`, description: meta.blurb }
25
+ }
26
+
27
+ export default async function TutorialPage({
28
+ params,
29
+ }: {
30
+ params: Promise<{ slug: string }>
31
+ }) {
32
+ const { slug } = await params
33
+ const meta = getTutorialMeta(slug)
34
+ const source = readTutorial(slug)
35
+ if (!meta || source === null) {
36
+ notFound()
37
+ }
38
+
39
+ return (
40
+ <div className="min-h-screen bg-background">
41
+ <Navigation />
42
+
43
+ <main className="mx-auto w-full max-w-[52rem] px-4 pb-24 pt-12 sm:px-8">
44
+ <Link
45
+ href="/help"
46
+ className="inline-flex items-center gap-1.5 font-mono text-[11px] uppercase tracking-[0.12em] text-[color:var(--fg-muted)] transition-colors hover:text-[color:var(--fg)]"
47
+ >
48
+ <ArrowLeft className="h-3.5 w-3.5" aria-hidden />
49
+ All guides
50
+ </Link>
51
+
52
+ <div className="kicker mt-6">{meta.audience}</div>
53
+
54
+ <article className="mt-3">
55
+ <TutorialMarkdown source={source} />
56
+ </article>
57
+
58
+ <section className="mt-14 flex flex-wrap gap-3 border-t border-[color:var(--border-soft)] pt-10">
59
+ <Link href="/help" className="btn-ec outline">
60
+ <ArrowLeft className="h-3.5 w-3.5" aria-hidden />
61
+ Back to Help
62
+ </Link>
63
+ <ReplayIntroButton />
64
+ </section>
65
+ </main>
66
+ </div>
67
+ )
68
+ }
app/help/page.tsx ADDED
@@ -0,0 +1,363 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import Link from "next/link"
2
+ import type { Metadata } from "next"
3
+ import { ArrowRight, ExternalLink, FileText } from "lucide-react"
4
+
5
+ import { CiteSection, PAPER_URL } from "@/components/cite-section"
6
+ import { Navigation } from "@/components/navigation"
7
+ import { ReplayIntroButton } from "@/components/replay-intro-button"
8
+ import { DOCS, TUTORIALS } from "@/lib/tutorials"
9
+
10
+ export const metadata: Metadata = {
11
+ title: "Help",
12
+ description:
13
+ "Learn how to read Evaluation Cards: a quickstart, stakeholder guides, documentation, and how to contribute.",
14
+ }
15
+
16
+ const quickstart = TUTORIALS.find((t) => t.slug === "quickstart")!
17
+ const stakeholderGuides = TUTORIALS.filter((t) => t.slug !== "quickstart")
18
+
19
+ const linkCls = "text-[color:var(--fg)] underline underline-offset-2 hover:opacity-80"
20
+ const EEE_SITE = "https://evalevalai.com/every_eval_ever/"
21
+ const EEE_ISSUES = "https://github.com/evaleval/every_eval_ever/issues"
22
+ const HF_DISCUSSIONS = "https://huggingface.co/spaces/evaleval/general-eval-card/discussions"
23
+ const ROADMAP = "https://changemap.co/evaleval/evalcards/"
24
+
25
+ export default function HelpPage() {
26
+ return (
27
+ <div className="min-h-screen bg-background">
28
+ <Navigation />
29
+
30
+ <main className="mx-auto w-full max-w-[64rem] px-4 pb-24 pt-12 sm:px-8">
31
+ {/* HEADER --------------------------------------------------------- */}
32
+ <div className="kicker">Help</div>
33
+ <h1
34
+ className="mt-2 mb-7"
35
+ style={{
36
+ fontSize: "clamp(40px, 5.2vw, 56px)",
37
+ fontWeight: 700,
38
+ letterSpacing: "-0.03em",
39
+ lineHeight: 1.05,
40
+ color: "var(--fg)",
41
+ }}
42
+ >
43
+ How to use Evaluation Cards.
44
+ </h1>
45
+ <p className="mb-8 text-[19px] leading-[1.6] text-[color:var(--fg-muted)]">
46
+ New here? Start with the quickstart, then dive into a guide written for your role.
47
+ You can replay the intro tour at any time.
48
+ </p>
49
+ <ReplayIntroButton />
50
+
51
+ {/* QUICKSTART ----------------------------------------------------- */}
52
+ <section className="mt-14 mb-14">
53
+ <div className="section-head">
54
+ <h2>Quickstart</h2>
55
+ </div>
56
+ <Link
57
+ href={`/help/${quickstart.slug}`}
58
+ className="group flex flex-col gap-3 border border-[color:var(--border-soft)] bg-[color:var(--fg)] p-7 text-[color:var(--bg)] sm:flex-row sm:items-center sm:justify-between"
59
+ >
60
+ <div>
61
+ <div className="kicker mb-2" style={{ color: "var(--accent)" }}>
62
+ {quickstart.audience}
63
+ </div>
64
+ <h3 className="m-0 mb-1.5 text-xl font-semibold">{quickstart.title}</h3>
65
+ <p
66
+ className="m-0 max-w-[44ch] text-[14px] leading-[1.6]"
67
+ style={{ color: "color-mix(in srgb, var(--bg) 78%, transparent)" }}
68
+ >
69
+ {quickstart.blurb}
70
+ </p>
71
+ </div>
72
+ <span className="inline-flex shrink-0 items-center gap-2 font-mono text-[11px] uppercase tracking-[0.12em]">
73
+ Start reading
74
+ <ArrowRight className="h-4 w-4 transition-transform group-hover:translate-x-0.5" aria-hidden />
75
+ </span>
76
+ </Link>
77
+ </section>
78
+
79
+ {/* TUTORIALS BY STAKEHOLDER --------------------------------------- */}
80
+ <section className="mb-14">
81
+ <div className="section-head">
82
+ <h2>Tutorials by stakeholder</h2>
83
+ </div>
84
+ <p className="mb-5 max-w-[700px] text-[15px] leading-[1.7] text-[color:var(--fg-muted)]">
85
+ Each guide reads the same record through a different lens. Pick the one closest to
86
+ how you'll use Evaluation Cards.
87
+ </p>
88
+ <div className="grid gap-5 sm:grid-cols-2">
89
+ {stakeholderGuides.map((guide) => (
90
+ <Link
91
+ key={guide.slug}
92
+ href={`/help/${guide.slug}`}
93
+ className="group flex flex-col border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px] transition-colors hover:border-[color:var(--border-strong)]"
94
+ >
95
+ <div className="kicker mb-2">{guide.audience}</div>
96
+ <h3 className="m-0 mb-2 flex items-center gap-2 text-base font-semibold tracking-[-0.005em] text-[color:var(--fg)]">
97
+ {guide.title}
98
+ <ArrowRight
99
+ className="h-3.5 w-3.5 text-[color:var(--fg-subtle)] transition-transform group-hover:translate-x-0.5"
100
+ aria-hidden
101
+ />
102
+ </h3>
103
+ <p className="m-0 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)]">
104
+ {guide.blurb}
105
+ </p>
106
+ </Link>
107
+ ))}
108
+ </div>
109
+ </section>
110
+
111
+ {/* DOCUMENTATION -------------------------------------------------- */}
112
+ <section className="mb-14">
113
+ <div className="section-head">
114
+ <h2>Documentation</h2>
115
+ </div>
116
+ <p className="mb-5 max-w-[700px] text-[15px] leading-[1.7] text-[color:var(--fg-muted)]">
117
+ Deeper, more technical references for contributing to and working with the data
118
+ behind Evaluation Cards.
119
+ </p>
120
+ <div className="grid gap-5 sm:grid-cols-2">
121
+ {DOCS.map((doc) => (
122
+ <Link
123
+ key={doc.slug}
124
+ href={`/help/${doc.slug}`}
125
+ className="group flex flex-col border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px] transition-colors hover:border-[color:var(--border-strong)]"
126
+ >
127
+ <div className="kicker mb-2 flex items-center gap-1.5">
128
+ <FileText className="h-3 w-3" aria-hidden />
129
+ {doc.audience}
130
+ </div>
131
+ <h3 className="m-0 mb-2 flex items-center gap-2 text-base font-semibold tracking-[-0.005em] text-[color:var(--fg)]">
132
+ {doc.title}
133
+ <ArrowRight
134
+ className="h-3.5 w-3.5 text-[color:var(--fg-subtle)] transition-transform group-hover:translate-x-0.5"
135
+ aria-hidden
136
+ />
137
+ </h3>
138
+ <p className="m-0 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)]">
139
+ {doc.blurb}
140
+ </p>
141
+ </Link>
142
+ ))}
143
+
144
+ {/* External: how to contribute evaluation results to EEE */}
145
+ <a
146
+ href="https://evalevalai.com/every_eval_ever/"
147
+ target="_blank"
148
+ rel="noreferrer"
149
+ className="group flex flex-col border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px] transition-colors hover:border-[color:var(--border-strong)]"
150
+ >
151
+ <div className="kicker mb-2 flex items-center gap-1.5">
152
+ <ExternalLink className="h-3 w-3" aria-hidden />
153
+ External · EvalEval
154
+ </div>
155
+ <h3 className="m-0 mb-2 flex items-center gap-2 text-base font-semibold tracking-[-0.005em] text-[color:var(--fg)]">
156
+ Add results to Every Eval Ever
157
+ <ExternalLink
158
+ className="h-3.5 w-3.5 text-[color:var(--fg-subtle)] transition-transform group-hover:-translate-y-0.5"
159
+ aria-hidden
160
+ />
161
+ </h3>
162
+ <p className="m-0 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)]">
163
+ The Every Eval Ever contributor site explains how to add evaluation results to the
164
+ datastore that powers Evaluation Cards.
165
+ </p>
166
+ </a>
167
+ </div>
168
+ <p className="mt-4 text-[13px] leading-[1.6] text-[color:var(--fg-subtle)]">
169
+ Suggest missing documentation on our{" "}
170
+ <a
171
+ href="https://changemap.co/evaleval/evalcards/"
172
+ target="_blank"
173
+ rel="noreferrer"
174
+ className="underline underline-offset-2 hover:text-[color:var(--fg)]"
175
+ >
176
+ public roadmap
177
+ </a>{" "}
178
+ and we'll make sure to add it!
179
+ </p>
180
+ </section>
181
+
182
+ {/* HOW TO CONTRIBUTE ---------------------------------------------- */}
183
+ <section id="how-to-contribute" className="mb-8 scroll-mt-24">
184
+ <div className="section-head">
185
+ <h2>How to contribute</h2>
186
+ </div>
187
+ <p className="mb-5 max-w-[720px] text-[15px] leading-[1.7] text-[color:var(--fg-muted)]">
188
+ Evaluation Cards is a living, community artifact — its coverage and usefulness grow as
189
+ people report, upload, use, and cite it. Here's what helps most, depending on who you
190
+ are.
191
+ </p>
192
+ <div className="grid gap-5 sm:grid-cols-2">
193
+ {/* MODEL DEVELOPERS */}
194
+ <div className="border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px]">
195
+ <div className="kicker mb-2">Model developers</div>
196
+ <ul className="m-0 list-disc space-y-2 pl-4 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)] marker:text-[color:var(--fg-subtle)]">
197
+ <li>
198
+ Report your model's results to{" "}
199
+ <a href={EEE_SITE} target="_blank" rel="noreferrer" className={linkCls}>
200
+ Every Eval Ever
201
+ </a>{" "}
202
+ so they show up here in context.
203
+ </li>
204
+ <li>
205
+ Already on EEE?{" "}
206
+ <Link href="/help/cross-post-to-hugging-face" className={linkCls}>
207
+ Cross-post them to Hugging Face
208
+ </Link>{" "}
209
+ so your scores appear on the model page with a backlink.
210
+ </li>
211
+ <li>
212
+ Document the run-level details that raise your signals — temperature and max
213
+ tokens, the harness, and (for agentic evaluations) the eval plan and limits.
214
+ </li>
215
+ <li>
216
+ See a wrong or missing number for your model? Flag it in the{" "}
217
+ <a href={HF_DISCUSSIONS} target="_blank" rel="noreferrer" className={linkCls}>
218
+ Space discussions
219
+ </a>{" "}
220
+ or via each record's correction path.
221
+ </li>
222
+ </ul>
223
+ </div>
224
+
225
+ {/* EVALUATION DEVELOPERS */}
226
+ <div className="border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px]">
227
+ <div className="kicker mb-2">Evaluation developers</div>
228
+ <ul className="m-0 list-disc space-y-2 pl-4 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)] marker:text-[color:var(--fg-subtle)]">
229
+ <li>
230
+ Upload your benchmark's results to{" "}
231
+ <a href={EEE_SITE} target="_blank" rel="noreferrer" className={linkCls}>
232
+ Every Eval Ever
233
+ </a>{" "}
234
+ so others can find, run, and reuse them.
235
+ </li>
236
+ <li>
237
+ Fill in your benchmark's metadata — goals, construct, scoring rubric, intended
238
+ uses, and limitations — to raise its{" "}
239
+ <Link href="/help/how-signals-are-computed" className={linkCls}>
240
+ completeness score
241
+ </Link>
242
+ .
243
+ </li>
244
+ <li>
245
+ Report schema gaps or data issues on the{" "}
246
+ <a href={EEE_ISSUES} target="_blank" rel="noreferrer" className={linkCls}>
247
+ EEE issue tracker
248
+ </a>
249
+ .
250
+ </li>
251
+ </ul>
252
+ </div>
253
+
254
+ {/* RESEARCHERS */}
255
+ <div className="border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px]">
256
+ <div className="kicker mb-2">Researchers</div>
257
+ <ul className="m-0 list-disc space-y-2 pl-4 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)] marker:text-[color:var(--fg-subtle)]">
258
+ <li>
259
+ Use Evaluation Cards in your model-, evaluation-, or field-level analysis — and{" "}
260
+ <Link href="/about#how-to-cite" className={linkCls}>
261
+ cite the paper
262
+ </Link>{" "}
263
+ when you build on it.
264
+ </li>
265
+ <li>
266
+ Report third-party results you've run to{" "}
267
+ <a href={EEE_SITE} target="_blank" rel="noreferrer" className={linkCls}>
268
+ Every Eval Ever
269
+ </a>{" "}
270
+ — independent numbers are first-class here.
271
+ </li>
272
+ <li>
273
+ Flag discrepancies or suggest methodology improvements on the{" "}
274
+ <a href={EEE_ISSUES} target="_blank" rel="noreferrer" className={linkCls}>
275
+ issue tracker
276
+ </a>{" "}
277
+ or in the{" "}
278
+ <a href={HF_DISCUSSIONS} target="_blank" rel="noreferrer" className={linkCls}>
279
+ discussions
280
+ </a>
281
+ .
282
+ </li>
283
+ <li>Spread the word — share it with collaborators and on socials.</li>
284
+ </ul>
285
+ </div>
286
+
287
+ {/* POLICYMAKERS */}
288
+ <div className="border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] p-[22px]">
289
+ <div className="kicker mb-2">Policymakers</div>
290
+ <ul className="m-0 list-disc space-y-2 pl-4 text-[13.5px] leading-[1.6] text-[color:var(--fg-muted)] marker:text-[color:var(--fg-subtle)]">
291
+ <li>
292
+ Consult Evaluation Cards as an evidence base — what's documented, who reported it,
293
+ and how comparable it is.
294
+ </li>
295
+ <li>
296
+ <Link href="/about#how-to-cite" className={linkCls}>
297
+ Cite the paper
298
+ </Link>{" "}
299
+ in reports and briefings, and point colleagues to the site.
300
+ </li>
301
+ <li>
302
+ Tell us what evidence you need for decisions — suggest features on the{" "}
303
+ <a href={ROADMAP} target="_blank" rel="noreferrer" className={linkCls}>
304
+ public roadmap
305
+ </a>{" "}
306
+ or via the{" "}
307
+ <Link href="/feedback" className={linkCls}>
308
+ feedback form
309
+ </Link>
310
+ .
311
+ </li>
312
+ <li>Spread the word so more of the field reports legibly.</li>
313
+ </ul>
314
+ </div>
315
+ </div>
316
+
317
+ <p className="mt-5 text-[14px] leading-[1.7] text-[color:var(--fg-muted)]">
318
+ Not sure where something fits? The{" "}
319
+ <a href={ROADMAP} target="_blank" rel="noreferrer" className={linkCls}>
320
+ public roadmap
321
+ </a>
322
+ , the{" "}
323
+ <Link href="/feedback" className={linkCls}>
324
+ feedback form
325
+ </Link>
326
+ , the{" "}
327
+ <a href={EEE_ISSUES} target="_blank" rel="noreferrer" className={linkCls}>
328
+ EEE issue tracker
329
+ </a>
330
+ , and the{" "}
331
+ <a href={HF_DISCUSSIONS} target="_blank" rel="noreferrer" className={linkCls}>
332
+ Space discussions
333
+ </a>{" "}
334
+ are always open.
335
+ </p>
336
+ </section>
337
+
338
+ {/* HOW TO CITE ---------------------------------------------------- */}
339
+ <section id="how-to-cite" className="mb-8 scroll-mt-24">
340
+ <div className="section-head">
341
+ <h2>How to cite</h2>
342
+ </div>
343
+ <CiteSection />
344
+ </section>
345
+
346
+ {/* CTA ROW -------------------------------------------------------- */}
347
+ <section className="mt-12 flex flex-wrap gap-3 border-t border-[color:var(--border-soft)] pt-10">
348
+ <ReplayIntroButton />
349
+ <Link href="/" className="btn-ec outline">
350
+ Back to home
351
+ </Link>
352
+ <Link href="/about" className="btn-ec outline">
353
+ About Evaluation Cards
354
+ </Link>
355
+ <a href={PAPER_URL} target="_blank" rel="noreferrer" className="btn-ec outline">
356
+ Read the paper
357
+ <ExternalLink className="h-3.5 w-3.5" aria-hidden />
358
+ </a>
359
+ </section>
360
+ </main>
361
+ </div>
362
+ )
363
+ }
app/layout.tsx CHANGED
@@ -3,6 +3,8 @@ import type { Metadata } from "next"
3
  import "./globals.css"
4
  import { AudienceModeProvider } from "@/components/audience-mode-provider"
5
  import { BackendRefreshListener } from "@/components/backend-refresh-listener"
 
 
6
  import { ThemeProvider } from "@/components/theme-provider"
7
 
8
  const SITE_URL = "https://evalcards.evalevalai.com"
@@ -67,8 +69,11 @@ export default function RootLayout({
67
  <body className="font-sans">
68
  <ThemeProvider attribute="class" defaultTheme="system" enableSystem disableTransitionOnChange>
69
  <AudienceModeProvider>
70
- <BackendRefreshListener />
71
- {children}
 
 
 
72
  </AudienceModeProvider>
73
  </ThemeProvider>
74
  </body>
 
3
  import "./globals.css"
4
  import { AudienceModeProvider } from "@/components/audience-mode-provider"
5
  import { BackendRefreshListener } from "@/components/backend-refresh-listener"
6
+ import { QuickStartProvider } from "@/components/quick-start"
7
+ import { SiteFooter } from "@/components/site-footer"
8
  import { ThemeProvider } from "@/components/theme-provider"
9
 
10
  const SITE_URL = "https://evalcards.evalevalai.com"
 
69
  <body className="font-sans">
70
  <ThemeProvider attribute="class" defaultTheme="system" enableSystem disableTransitionOnChange>
71
  <AudienceModeProvider>
72
+ <QuickStartProvider>
73
+ <BackendRefreshListener />
74
+ {children}
75
+ <SiteFooter />
76
+ </QuickStartProvider>
77
  </AudienceModeProvider>
78
  </ThemeProvider>
79
  </body>
components/cite-block.tsx ADDED
@@ -0,0 +1,47 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client"
2
+
3
+ import { useState } from "react"
4
+ import { Check, Copy } from "lucide-react"
5
+
6
+ /** A labeled, copy-pasteable BibTeX block. */
7
+ export function CiteBlock({ bibtex, label = "BibTeX" }: { bibtex: string; label?: string }) {
8
+ const [copied, setCopied] = useState(false)
9
+
10
+ const copy = async () => {
11
+ try {
12
+ await navigator.clipboard.writeText(bibtex)
13
+ setCopied(true)
14
+ setTimeout(() => setCopied(false), 1800)
15
+ } catch {
16
+ // clipboard unavailable — the text is still selectable in the <pre>.
17
+ }
18
+ }
19
+
20
+ return (
21
+ <div className="border border-[color:var(--border-soft)]">
22
+ <div className="flex items-center justify-between border-b border-[color:var(--border-soft)] bg-[color:var(--bg-warm)] px-4 py-2.5">
23
+ <span className="kicker">{label}</span>
24
+ <button
25
+ type="button"
26
+ onClick={copy}
27
+ className="inline-flex items-center gap-1.5 font-mono text-[11px] uppercase tracking-[0.12em] text-[color:var(--fg-muted)] transition-colors hover:text-[color:var(--fg)]"
28
+ >
29
+ {copied ? (
30
+ <>
31
+ <Check className="h-3.5 w-3.5 text-[color:var(--accent)]" aria-hidden />
32
+ Copied
33
+ </>
34
+ ) : (
35
+ <>
36
+ <Copy className="h-3.5 w-3.5" aria-hidden />
37
+ Copy
38
+ </>
39
+ )}
40
+ </button>
41
+ </div>
42
+ <pre className="m-0 overflow-x-auto p-4 font-mono text-[12px] leading-[1.6] text-[color:var(--fg)]">
43
+ <code>{bibtex}</code>
44
+ </pre>
45
+ </div>
46
+ )
47
+ }
components/cite-section.tsx ADDED
@@ -0,0 +1,87 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import Link from "next/link"
2
+
3
+ import { CiteBlock } from "@/components/cite-block"
4
+ import { cn } from "@/lib/utils"
5
+
6
+ export const PAPER_URL = "https://arxiv.org/abs/2606.09809"
7
+ export const PAPER_BIBTEX = `@article{ghosh2026evaluationcards,
8
+ title = {Evaluation Cards: An Interpretive Layer for AI Evaluation Reporting},
9
+ author = {Ghosh, Avijit and Reuel, Anka and Chim, Jenny and Kennedy, Wm. Matthew and Yadav, Srishti and Mickel, Jennifer and Long, Yanan and Tran, Andrew and Kornilova, Anastassia and Stachura, Damian and Klyman, Kevin and Friedrich, Felix and Sania, Jeba and Lamparth, Max and Batzner, Jan and Mishra, Anoop and Habba, Eliya and Hao, Yixiong and Heath, Nathan and Rismani, Shalaleh and Gohar, Usman and Loehr, Andrea and Manheim, David and Dhar, Ruchira and Nelaturu, Sree Harsha and Sinha, Aarush and Choshen, Leshem and Sharma, Drishti and Khire, Ishan and Saha, Amit and Sahoo, Subramanyam and Hardy, Michael and Riegler, Michael Alexander and Manghnani, Kabir and Lin, Michelle and Jiang, Yanan and Huang, Yilin and Yehudai, Asaf and Ji, Jessica and Hofmann, Aris and Akhtar, Mubashara and Moniz, Nuno and Jernite, Yacine and Biderman, Stella and Talat, Zeerak and Koyejo, Sanmi and Kochenderfer, Mykel and Solaiman, Irene},
10
+ journal = {arXiv preprint arXiv:2606.09809},
11
+ year = {2026},
12
+ url = {https://arxiv.org/abs/2606.09809}
13
+ }`
14
+
15
+ export const EEE_BIBTEX = `@misc{evaleval2026everyevalever,
16
+ title = {Every Eval Ever: Toward a Common Language for AI Eval Reporting},
17
+ author = {Jan Batzner and Leshem Choshen and Avijit Ghosh and Sree Harsha Nelaturu and Anastassia Kornilova and Damian Stachura and Yifan Mai and Asaf Yehudai and Anka Reuel and Irene Solaiman and Stella Biderman},
18
+ year = {2026},
19
+ month = {February},
20
+ url = {https://evalevalai.com/infrastructure/2026/02/17/everyevalever-launch/},
21
+ note = {Blog Post, EvalEval Coalition}
22
+ }`
23
+
24
+ /**
25
+ * The "How to cite" body — share note, reference, copy-pasteable BibTeX. Shared
26
+ * by the About and Help pages so the citation stays in one place. Pass
27
+ * `showCorrection` to include the About page's correction card.
28
+ */
29
+ export function CiteSection({ showCorrection = false }: { showCorrection?: boolean }) {
30
+ return (
31
+ <>
32
+ <p className="mb-5 max-w-[700px] text-[15px] leading-[1.7] text-[color:var(--fg-muted)]">
33
+ If you find this effort useful, please consider citing our paper and sharing our work on
34
+ socials.
35
+ </p>
36
+ <div className={cn("mb-5 grid gap-5", showCorrection && "lg:grid-cols-2")}>
37
+ <div className="border border-[color:var(--border-soft)] p-[22px]">
38
+ <div className="kicker mb-2.5">Reference</div>
39
+ <p className="m-0 text-[13.5px] leading-[1.7] text-[color:var(--fg)]">
40
+ Ghosh, A., Reuel, A., Chim, J., et al. (2026). Evaluation Cards: An Interpretive Layer
41
+ for AI Evaluation Reporting.{" "}
42
+ <a
43
+ href={PAPER_URL}
44
+ target="_blank"
45
+ rel="noreferrer"
46
+ className="underline underline-offset-2"
47
+ >
48
+ arXiv:2606.09809
49
+ </a>
50
+ .
51
+ </p>
52
+ </div>
53
+ {showCorrection && (
54
+ <div className="border border-[color:var(--border-soft)] p-[22px]">
55
+ <div className="kicker mb-2.5">Submit a correction</div>
56
+ <p className="m-0 text-[13.5px] leading-[1.65] text-[color:var(--fg-muted)]">
57
+ Spotted a wrong or missing number? Send it through our{" "}
58
+ <Link
59
+ href="/feedback"
60
+ className="text-[color:var(--fg)] underline underline-offset-2"
61
+ >
62
+ feedback form
63
+ </Link>{" "}
64
+ with a source, and we'll get it corrected. Coverage improves as developers and third
65
+ parties publish.
66
+ </p>
67
+ </div>
68
+ )}
69
+ </div>
70
+ <CiteBlock bibtex={PAPER_BIBTEX} label="BibTeX · Evaluation Cards" />
71
+
72
+ <p className="mt-6 mb-3 max-w-[700px] text-[14px] leading-[1.7] text-[color:var(--fg-muted)]">
73
+ <a
74
+ href="https://evalevalai.com/every_eval_ever/"
75
+ target="_blank"
76
+ rel="noreferrer"
77
+ className="text-[color:var(--fg)] underline underline-offset-2"
78
+ >
79
+ Every Eval Ever
80
+ </a>{" "}
81
+ (EEE) is a sister project and one of the data sources that powers Evaluation Cards — please
82
+ show it some love and cite it too. 💜
83
+ </p>
84
+ <CiteBlock bibtex={EEE_BIBTEX} label="BibTeX · Every Eval Ever" />
85
+ </>
86
+ )
87
+ }
components/navigation.tsx CHANGED
@@ -31,6 +31,11 @@ export function Navigation() {
31
  label: "Evaluations",
32
  isActive: pathname === "/evals" || pathname?.startsWith("/evals/"),
33
  },
 
 
 
 
 
34
  {
35
  href: "/about",
36
  label: "About",
 
31
  label: "Evaluations",
32
  isActive: pathname === "/evals" || pathname?.startsWith("/evals/"),
33
  },
34
+ {
35
+ href: "/help",
36
+ label: "Help",
37
+ isActive: pathname === "/help" || pathname?.startsWith("/help/"),
38
+ },
39
  {
40
  href: "/about",
41
  label: "About",
components/quick-start.tsx ADDED
@@ -0,0 +1,217 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client"
2
+
3
+ import { createContext, useContext, useEffect, useMemo, useState } from "react"
4
+ import Link from "next/link"
5
+ import {
6
+ ArrowRight,
7
+ BarChart3,
8
+ BookOpen,
9
+ Boxes,
10
+ FlaskConical,
11
+ Layers,
12
+ ShieldQuestion,
13
+ } from "lucide-react"
14
+
15
+ import {
16
+ Dialog,
17
+ DialogContent,
18
+ DialogDescription,
19
+ DialogTitle,
20
+ } from "@/components/ui/dialog"
21
+ import { cn } from "@/lib/utils"
22
+
23
+ const STORAGE_KEY = "eval-cards-onboarding-seen"
24
+
25
+ interface QuickStartContextValue {
26
+ /** Open the welcome tour (used by the footer + Help page "replay" links). */
27
+ open: () => void
28
+ }
29
+
30
+ const QuickStartContext = createContext<QuickStartContextValue | null>(null)
31
+
32
+ interface Slide {
33
+ icon: React.ComponentType<{ className?: string }>
34
+ kicker: string
35
+ title: string
36
+ body: string
37
+ }
38
+
39
+ const SLIDES: Slide[] = [
40
+ {
41
+ icon: BookOpen,
42
+ kicker: "Welcome",
43
+ title: "What this is",
44
+ body: "Evaluation Cards collects how AI models have been tested across lots of benchmarks. A single score rarely tells you much on its own, so we give you everything you need to read one: the evaluation results, the benchmark's metadata, how the run was set up, and our interpretive signals. And unlike any other artefact out there, you can see those results reported side by side, which makes them easy to compare.",
45
+ },
46
+ {
47
+ icon: Layers,
48
+ kicker: "Reader modes",
49
+ title: "Two ways to read",
50
+ body: "Use the toggle in the top bar to switch views. Research shows the methodology: the settings, the configs, and what's missing. Summary keeps it plain. Either way you're looking at the same data.",
51
+ },
52
+ {
53
+ icon: BarChart3,
54
+ kicker: "Signals",
55
+ title: "Four things we check",
56
+ body: "Each result is scored on four things: whether it can be reproduced, how complete it is, where it came from, and whether it's fair to compare with other scores. Together they tell you how much to trust a number.",
57
+ },
58
+ {
59
+ icon: Boxes,
60
+ kicker: "Models",
61
+ title: "The Models tab",
62
+ body: "This is every model we track. Search or sort by developer, size, or release date, open one to see its full card, and pick up to four to compare.",
63
+ },
64
+ {
65
+ icon: FlaskConical,
66
+ kicker: "Evaluations",
67
+ title: "The Evaluations tab",
68
+ body: "Here you'll find the benchmarks, grouped from broad families down to single metrics. Filter by risk area or agentic tasks, and open any benchmark to see what it tests, where it falls short, and who's reported results on it.",
69
+ },
70
+ {
71
+ icon: ShieldQuestion,
72
+ kicker: "How we handle gaps",
73
+ title: "We don't fill in the blanks",
74
+ body: "If something wasn't reported, we leave it blank instead of guessing or estimating. A missing safety test tells you something too, so we'd rather show the gap than hide it.",
75
+ },
76
+ ]
77
+
78
+ export function QuickStartProvider({ children }: { children: React.ReactNode }) {
79
+ const [open, setOpen] = useState(false)
80
+
81
+ // Auto-open on a visitor's first time, mirroring the audience-mode pattern.
82
+ useEffect(() => {
83
+ try {
84
+ if (!window.localStorage.getItem(STORAGE_KEY)) {
85
+ setOpen(true)
86
+ }
87
+ } catch {
88
+ // localStorage unavailable (e.g. privacy mode) — skip the tour silently.
89
+ }
90
+ }, [])
91
+
92
+ const markSeen = () => {
93
+ try {
94
+ window.localStorage.setItem(STORAGE_KEY, "1")
95
+ } catch {
96
+ // ignore
97
+ }
98
+ }
99
+
100
+ const handleOpenChange = (next: boolean) => {
101
+ setOpen(next)
102
+ if (!next) markSeen()
103
+ }
104
+
105
+ const value = useMemo<QuickStartContextValue>(() => ({ open: () => setOpen(true) }), [])
106
+
107
+ return (
108
+ <QuickStartContext.Provider value={value}>
109
+ {children}
110
+ <QuickStartDialog open={open} onOpenChange={handleOpenChange} />
111
+ </QuickStartContext.Provider>
112
+ )
113
+ }
114
+
115
+ export function useQuickStart(): QuickStartContextValue {
116
+ const context = useContext(QuickStartContext)
117
+ if (!context) {
118
+ throw new Error("useQuickStart must be used within a QuickStartProvider")
119
+ }
120
+ return context
121
+ }
122
+
123
+ function QuickStartDialog({
124
+ open,
125
+ onOpenChange,
126
+ }: {
127
+ open: boolean
128
+ onOpenChange: (next: boolean) => void
129
+ }) {
130
+ const [step, setStep] = useState(0)
131
+
132
+ // Reset to the first slide whenever the dialog is (re)opened.
133
+ useEffect(() => {
134
+ if (open) setStep(0)
135
+ }, [open])
136
+
137
+ const slide = SLIDES[step]
138
+ const Icon = slide.icon
139
+ const isLast = step === SLIDES.length - 1
140
+
141
+ return (
142
+ <Dialog open={open} onOpenChange={onOpenChange}>
143
+ <DialogContent className="gap-0 p-0 sm:max-w-[480px]">
144
+ <div className="p-7">
145
+ <div className="mb-5 flex h-11 w-11 items-center justify-center border border-[color:var(--border-soft)] bg-[color:var(--bg-warm)]">
146
+ <Icon className="h-5 w-5 text-[color:var(--accent)]" />
147
+ </div>
148
+ <div className="kicker mb-2">{slide.kicker}</div>
149
+ <DialogTitle className="text-[22px] font-semibold tracking-[-0.01em] text-[color:var(--fg)]">
150
+ {slide.title}
151
+ </DialogTitle>
152
+ <DialogDescription className="mt-2.5 text-[15px] leading-[1.65] text-[color:var(--fg-muted)]">
153
+ {slide.body}
154
+ </DialogDescription>
155
+
156
+ {isLast && (
157
+ <div className="mt-5 flex flex-wrap gap-2.5">
158
+ <Link href="/models" className="btn-ec" onClick={() => onOpenChange(false)}>
159
+ Explore models
160
+ <ArrowRight className="h-3.5 w-3.5" aria-hidden />
161
+ </Link>
162
+ <Link href="/help" className="btn-ec outline" onClick={() => onOpenChange(false)}>
163
+ Open the full guide
164
+ </Link>
165
+ </div>
166
+ )}
167
+ </div>
168
+
169
+ {/* Footer: progress dots + navigation */}
170
+ <div className="flex items-center justify-between border-t border-[color:var(--border-soft)] px-7 py-4">
171
+ <div className="flex items-center gap-1.5" aria-hidden>
172
+ {SLIDES.map((_, i) => (
173
+ <span
174
+ key={i}
175
+ className={cn(
176
+ "h-1.5 w-1.5 rounded-full transition-colors",
177
+ i === step ? "bg-[color:var(--fg)]" : "bg-[color:var(--border-strong)]"
178
+ )}
179
+ />
180
+ ))}
181
+ </div>
182
+
183
+ <div className="flex items-center gap-2">
184
+ {step > 0 ? (
185
+ <button
186
+ type="button"
187
+ className="btn-ec ghost"
188
+ onClick={() => setStep((s) => Math.max(0, s - 1))}
189
+ >
190
+ Back
191
+ </button>
192
+ ) : (
193
+ <button type="button" className="btn-ec ghost" onClick={() => onOpenChange(false)}>
194
+ Skip
195
+ </button>
196
+ )}
197
+
198
+ {isLast ? (
199
+ <button type="button" className="btn-ec" onClick={() => onOpenChange(false)}>
200
+ Get started
201
+ </button>
202
+ ) : (
203
+ <button
204
+ type="button"
205
+ className="btn-ec"
206
+ onClick={() => setStep((s) => Math.min(SLIDES.length - 1, s + 1))}
207
+ >
208
+ Next
209
+ <ArrowRight className="h-3.5 w-3.5" aria-hidden />
210
+ </button>
211
+ )}
212
+ </div>
213
+ </div>
214
+ </DialogContent>
215
+ </Dialog>
216
+ )
217
+ }
components/replay-intro-button.tsx ADDED
@@ -0,0 +1,16 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client"
2
+
3
+ import { Play } from "lucide-react"
4
+
5
+ import { useQuickStart } from "@/components/quick-start"
6
+ import { cn } from "@/lib/utils"
7
+
8
+ export function ReplayIntroButton({ className }: { className?: string }) {
9
+ const { open } = useQuickStart()
10
+ return (
11
+ <button type="button" onClick={open} className={cn("btn-ec outline", className)}>
12
+ <Play className="h-3.5 w-3.5" aria-hidden />
13
+ Replay the intro
14
+ </button>
15
+ )
16
+ }
components/site-footer.tsx ADDED
@@ -0,0 +1,57 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client"
2
+
3
+ import Link from "next/link"
4
+
5
+ import { useQuickStart } from "@/components/quick-start"
6
+
7
+ export function SiteFooter() {
8
+ const { open } = useQuickStart()
9
+
10
+ return (
11
+ <footer className="border-t border-[color:var(--border-soft)] bg-[color:var(--bg-warm)]">
12
+ <div className="mx-auto flex w-full max-w-[96rem] flex-col gap-3 px-4 py-6 sm:flex-row sm:items-center sm:justify-between sm:px-8">
13
+ <span className="font-mono text-[11px] uppercase tracking-[0.12em] text-[color:var(--fg-subtle)]">
14
+ Evaluation Cards · EvalEval Coalition
15
+ </span>
16
+ <nav className="flex flex-wrap items-center gap-x-5 gap-y-2 font-mono text-[11px] uppercase tracking-[0.12em] text-[color:var(--fg-muted)]">
17
+ <Link href="/about" className="transition-colors hover:text-[color:var(--fg)]">
18
+ About
19
+ </Link>
20
+ <Link href="/help" className="transition-colors hover:text-[color:var(--fg)]">
21
+ Help
22
+ </Link>
23
+ <Link
24
+ href="/help#how-to-contribute"
25
+ className="transition-colors hover:text-[color:var(--fg)]"
26
+ >
27
+ How to contribute
28
+ </Link>
29
+ <Link
30
+ href="/about#how-to-cite"
31
+ className="transition-colors hover:text-[color:var(--fg)]"
32
+ >
33
+ How to cite
34
+ </Link>
35
+ <Link href="/feedback" className="transition-colors hover:text-[color:var(--fg)]">
36
+ Feedback
37
+ </Link>
38
+ <a
39
+ href="https://arxiv.org/abs/2606.09809"
40
+ target="_blank"
41
+ rel="noreferrer"
42
+ className="transition-colors hover:text-[color:var(--fg)]"
43
+ >
44
+ Paper
45
+ </a>
46
+ <button
47
+ type="button"
48
+ onClick={open}
49
+ className="uppercase tracking-[0.12em] transition-colors hover:text-[color:var(--fg)]"
50
+ >
51
+ Replay intro
52
+ </button>
53
+ </nav>
54
+ </div>
55
+ </footer>
56
+ )
57
+ }
components/tutorial-markdown.tsx ADDED
@@ -0,0 +1,101 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client"
2
+
3
+ import Link from "next/link"
4
+ import { ImageIcon } from "lucide-react"
5
+ import ReactMarkdown, { defaultUrlTransform } from "react-markdown"
6
+ import rehypeKatex from "rehype-katex"
7
+ import remarkGfm from "remark-gfm"
8
+ import remarkMath from "remark-math"
9
+
10
+ import { cn } from "@/lib/utils"
11
+
12
+ /**
13
+ * Renders a pre-processed tutorial markdown string (see lib/tutorials.ts) with
14
+ * the site's design tokens. Handles two source-specific concerns:
15
+ * - relative `*.md` / `../about` links are rewritten to in-app routes;
16
+ * - `placeholder:<file>` image sources render as styled "screenshot coming"
17
+ * callouts instead of broken images.
18
+ */
19
+ export function TutorialMarkdown({ source }: { source: string }) {
20
+ return (
21
+ <div className="tutorial-prose">
22
+ <ReactMarkdown
23
+ remarkPlugins={[remarkGfm, remarkMath]}
24
+ rehypePlugins={[rehypeKatex]}
25
+ // Preserve our internal `placeholder:` scheme for missing screenshots;
26
+ // react-markdown would otherwise sanitize the URL away.
27
+ urlTransform={(url) =>
28
+ url.startsWith("placeholder:") ? url : defaultUrlTransform(url)
29
+ }
30
+ components={{
31
+ a: ({ href, children }) => {
32
+ const target = resolveHref(String(href ?? ""))
33
+ if (target.external) {
34
+ return (
35
+ <a href={target.href} target="_blank" rel="noreferrer">
36
+ {children}
37
+ </a>
38
+ )
39
+ }
40
+ return <Link href={target.href}>{children}</Link>
41
+ },
42
+ img: ({ src, alt }) => {
43
+ const value = String(src ?? "")
44
+ if (value.startsWith("placeholder:")) {
45
+ return <ScreenshotPlaceholder file={value.slice("placeholder:".length)} note={alt} />
46
+ }
47
+ return (
48
+ <figure className="tut-figure">
49
+ <span className="tut-figure-frame block">
50
+ {/* eslint-disable-next-line @next/next/no-img-element */}
51
+ <img src={value} alt={alt ?? ""} loading="lazy" />
52
+ </span>
53
+ {alt ? <figcaption>{alt}</figcaption> : null}
54
+ </figure>
55
+ )
56
+ },
57
+ }}
58
+ >
59
+ {source}
60
+ </ReactMarkdown>
61
+ </div>
62
+ )
63
+ }
64
+
65
+ function resolveHref(href: string): { href: string; external: boolean } {
66
+ if (/^https?:\/\//.test(href) || href.startsWith("mailto:")) {
67
+ return { href, external: true }
68
+ }
69
+ if (href.startsWith("#")) {
70
+ return { href, external: false }
71
+ }
72
+ // Relative links between guides, e.g. "quickstart.md" → "/help/quickstart".
73
+ if (href.endsWith(".md")) {
74
+ const base = href.replace(/^.*\//, "").replace(/\.md$/, "")
75
+ return { href: `/help/${base}`, external: false }
76
+ }
77
+ // Relative escapes to the app root, e.g. "../about" → "/about".
78
+ if (href.startsWith("../") || href.startsWith("./")) {
79
+ const cleaned = href.replace(/^(\.\.\/|\.\/)+/, "")
80
+ return { href: `/${cleaned}`, external: false }
81
+ }
82
+ return { href, external: false }
83
+ }
84
+
85
+ function ScreenshotPlaceholder({ file, note }: { file: string; note?: string }) {
86
+ return (
87
+ <div
88
+ className={cn(
89
+ "my-6 flex gap-3 border border-dashed border-[color:var(--border-strong)]",
90
+ "bg-[color:var(--bg-subtle)] p-4 text-[color:var(--fg-muted)]"
91
+ )}
92
+ >
93
+ <ImageIcon className="mt-0.5 h-4 w-4 shrink-0 text-[color:var(--fg-subtle)]" aria-hidden />
94
+ <div className="min-w-0">
95
+ <div className="kicker mb-1">Screenshot coming</div>
96
+ <code className="font-mono text-[12px] text-[color:var(--fg)]">{file}</code>
97
+ {note ? <p className="m-0 mt-1.5 text-[13px] leading-[1.6]">{note}</p> : null}
98
+ </div>
99
+ </div>
100
+ )
101
+ }
content/tutorials/cross-post-to-hugging-face.md ADDED
@@ -0,0 +1,65 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Cross-post Every Eval Ever results to Hugging Face
2
+
3
+ *Send an Every Eval Ever (EEE) record to Hugging Face Community Evals so your score shows up on the model page — with a backlink to the full structured record.*
4
+
5
+ > **Audience:** contributors who already report evaluation results to [Every Eval Ever](https://github.com/evaleval/every_eval_ever). This is the more technical companion to the stakeholder guides.
6
+
7
+ ---
8
+
9
+ ## Why this exists
10
+
11
+ Every Eval Ever (EEE) launched in February 2026 as a project of the EvalEval Coalition — a cross-institutional effort to fix how AI evaluation results get reported. Eval results matter for capability measurement, safety, and governance, yet they are scattered and hard to compare: they live in papers, leaderboards, blog posts, and harness logs, each in its own format, and the same model on the same benchmark often returns different numbers depending on who ran it and how.
12
+
13
+ LLaMA 65B, for example, has been reported at both **63.7** and **48.8** on MMLU. That gap came down to the evaluation harness, not the model — and usually you can't even see a gap like that, because the metadata that would explain it isn't recorded.
14
+
15
+ EEE is the fix for the reporting side: **one JSON schema** for an evaluation result that records who ran it, which model, how it was accessed, the generation settings, and what the metric actually means — with an optional companion file for per-sample outputs. It takes in results from any source, so harness logs, leaderboard scrapes, and paper numbers all end up in the same shape. Since launching, the datastore on Hugging Face has grown to around **229,000 evaluation results** across more than **22,000 models** and **2,200 benchmarks**, pulled from **31** different reporting formats. Reproducing those runs from scratch would cost somewhere in the hundreds of thousands of dollars — a reasonable argument for not letting the data scatter once someone has paid to generate it.
16
+
17
+ ## What cross-posting does
18
+
19
+ You can now send your EEE results to **Hugging Face Community Evals** for official benchmarks. A converter takes an EEE record and writes the small YAML file Hugging Face expects, so you don't have to maintain the same result in two formats by hand.
20
+
21
+ Once you share, two things happen:
22
+
23
+ - Your score **appears on the Hugging Face model page** and is pulled into the benchmark's leaderboard.
24
+ - It carries a **source badge that links back to the full EEE record** — where the generation config, harness version, reproducibility notes, and any instance-level data live.
25
+
26
+ The two destinations do different jobs toward the same goal. Hugging Face puts your result where people look at models, with a link back to the source. EEE keeps the full structured record that makes the result interpretable — and powers Evaluation Cards on top of it. Send your data to both and the same evaluation ends up visible and legible at once, which is the point of reporting one at all.
27
+
28
+ ## How it works
29
+
30
+ Hugging Face stores eval scores in the model repo, as a YAML file under `.eval_results/`. The required fields are just the benchmark dataset, the task, and the value. The `source` block is optional — and it's the part that creates the backlink to EEE.
31
+
32
+ ```yaml
33
+ - dataset:
34
+ id: openai/gsm8k
35
+ task_id: gsm8k
36
+ value: 96.8
37
+ date: '2024-07-16'
38
+ notes: '8-shot CoT'
39
+ source:
40
+ url: https://huggingface.co/datasets/evaleval/EEE_datastore/blob/main/data/gsm8k/<dev>/<model>/<uuid>.json
41
+ name: EvalEval
42
+ ```
43
+
44
+ The converter fills this in from your existing record. It maps:
45
+
46
+ | EEE field | Hugging Face YAML field |
47
+ |---|---|
48
+ | `source_data.hf_repo` | `dataset.id` |
49
+ | `evaluation_name` | `task_id` |
50
+ | `score_details.score` | `value` |
51
+ | `evaluation_timestamp` | `date` |
52
+
53
+ …then drops in the `source` link to the per-record EEE JSON. It **skips any model repo that already has a YAML for the same dataset and task**, so re-running it won't open duplicate PRs.
54
+
55
+ ## Start here
56
+
57
+ If you already contribute to EEE, this is one extra step and the converter handles most of it:
58
+
59
+ 1. Submit your full record to the EEE datastore the usual way — the [GitHub repo](https://github.com/evaleval/every_eval_ever) has the contributor guide and converters.
60
+ 2. Run the converter to generate the Hugging Face YAML.
61
+ 3. Open the PR on the model's **Community** tab.
62
+
63
+ ---
64
+
65
+ *Adapted from "Cross-post your Every Eval Ever results onto Hugging Face model pages" — Netaluru Harsha, Nathan Habib, Avijit Ghosh.*
content/tutorials/evaluation-researchers.md ADDED
@@ -0,0 +1,106 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Evaluation Cards for Evaluation Researchers
2
+
3
+ *How to use Evaluation Cards as a working tool for studying, auditing, and comparing model evaluations.*
4
+
5
+ > **Prerequisite:** skim the [Quickstart](quickstart.md) first for the four signals and the five-level hierarchy.
6
+
7
+ ---
8
+
9
+ ## Why this matters for your work
10
+
11
+ If you study evaluations, you already know the core problem: published benchmark numbers are rarely accompanied by the prompts, decoding settings, harness versions, seeds, or evaluator identity needed to interpret or reproduce them. Evaluation Cards canonicalizes heterogeneous reporting into a single structured corpus where the **absence** of those details is recorded explicitly rather than silently dropped.
12
+
13
+ The design principles that matter most for research use:
14
+
15
+ - **Every score is attributed to its source document.** Provenance is first-class.
16
+ - **Missing values are never imputed.** A blank is "not reported," never a guessed number.
17
+ - **Evaluator identity is preserved.** First-party and third-party results are kept distinct.
18
+ - **Snapshot discipline.** No retroactive edits; corrections are versioned. Your analyses are reproducible against a dated snapshot.
19
+
20
+ ---
21
+
22
+ ## The Researcher View
23
+
24
+ The model card has two modes, toggled top-right. **Summary View** is for orientation; **Researcher View** is where you work.
25
+
26
+ > 🖼️ **Screenshot — `19-card-researcher-full.png`**
27
+ > *What to capture:* A model card (e.g. `/models/anthropic/claude-opus-4.7`) after clicking **Researcher View** — show the expanded per-result detail.
28
+
29
+ > 🖼️ **Screenshot — `20-card-researcher-top.png`**
30
+ > *What to capture:* The top of the Researcher View (the view toggle + the documentation summary line).
31
+
32
+ Researcher View exposes the per-result granularity behind the summary aggregates: setup variants, slices, metric paths, source harnesses, and the document each number came from.
33
+
34
+ ---
35
+
36
+ ## Working through a card, section by section
37
+
38
+ A model Evaluation Card is organized into four numbered sections.
39
+
40
+ ### §1 Identification
41
+ Model name, developer, release date, modalities (e.g. *image, text → text*), system ID, and last-updated. The stable identifier (`ec/models/<dev>/<model>`) is what you cite.
42
+
43
+ > 🖼️ **Screenshot — `15-card-identification.png`**
44
+ > *What to capture:* The §1 Identification block of a model card.
45
+
46
+ ### §2 Benchmark coverage
47
+ A benchmark-first view grouped by category, surfacing **setup spread** and **slice-vs-setup** differences up front. Watch the "slice spread" note (e.g. *"2 benchmarks include multiple slices or setups"*) — these are exactly the cases where naïve aggregation hides variance.
48
+
49
+ > 🖼️ **Screenshot — `16-card-coverage.png`**
50
+ > *What to capture:* The §2 Benchmark coverage section.
51
+
52
+ ### §3 Who reports what
53
+ A first-party / third-party split as a donut plus per-category bars. This is the provenance signal made concrete. In the captured example (*Claude Opus 4.7*, 39 results): **12 first-party (31%)** vs **27 third-party (69%)**, with per-category breakdowns (e.g. *Finance: 0 first-party · 3 third-party*; *Multimodal Input: 2 · 2*).
54
+
55
+ > 🖼️ **Screenshot — `17-card-who-reports.png`**
56
+ > *What to capture:* The §3 "Who reports what" section.
57
+
58
+ For research: a category that is **entirely first-party** is a known blind spot — there is no independent corroboration of those numbers.
59
+
60
+ ### §4 Reported metrics
61
+ Per-benchmark charts with controls to filter by **Source**, **Category**, and **Overlaps**, plus a family selector. Each chart marks direction ("higher is better"), the slices included, and the reporting org. This is where you read off the actual numbers and their setup context.
62
+
63
+ > 🖼️ **Screenshot — `18-card-metrics.png`**
64
+ > *What to capture:* The §4 Reported metrics section, ideally with a benchmark chart expanded.
65
+
66
+ > 🖼️ **Screenshot — `21-card-researcher-metrics.png`**
67
+ > *What to capture:* The §4 metrics area in **Researcher View**, showing the per-result detail (setup variants / slices).
68
+
69
+ ---
70
+
71
+ ## Reading the four signals rigorously
72
+
73
+ | Signal | What to inspect | Research caution |
74
+ |---|---|---|
75
+ | **Reproducibility** | Disclosure of setup variants, prompts, decoding params, harness version, seeds, code availability. | "Reproducible in principle" ≠ "reproduced." Only ~3% of scores have complete setup documentation corpus-wide. |
76
+ | **Completeness** | Coverage across capability / robustness / safety / fairness for the model class. | A complete *capability* record can still be silent on safety. Completeness is relative to expectations, not absolute. |
77
+ | **Provenance & Risk** | First- vs third-party; mapping to **IBM Risk Atlas** risk domains. | First-party numbers are not wrong, but they are not independent. Check §3 before ranking. |
78
+ | **Comparability** | Slice, metric variant, and unit differences within the same benchmark. | Two "MMLU" numbers may use different slices or metrics — flagged here. Do not rank across incomparable setups. |
79
+
80
+ ---
81
+
82
+ ## Comparing models and benchmarks
83
+
84
+ - **Models index** (`/models`): filter by parameter range (`< 1B` … `> 500B`, presets at 8B/12B/32B/128B, plus an *Unknown size* option), and toggle **Models ↔ Developers**.
85
+
86
+ > 🖼️ **Screenshot — `10-models-controls.png`**
87
+ > *What to capture:* The Models index controls (parameter slider, Models/Developers toggle, "selected to compare" counter).
88
+
89
+ - **Side-by-side compare:** select up to four models via the **Add to compare** buttons.
90
+ > ⚠️ *As of this writing the populated compare view is intermittently unavailable on the beta backend (cold-start errors). If it fails, retry after a few seconds.*
91
+
92
+ - **Evaluations index** (`/evals`): families filterable by **interaction style** (agent / non-agent) and category. Drill into a family at `/evals?family=<slug>` to see its benchmarks → slices → metrics.
93
+
94
+ > 🖼️ **Screenshot — `08-evals-family-expanded.png`**
95
+ > *What to capture:* A benchmark family detail page (e.g. `/evals?family=artificial-analysis`) showing its benchmarks and slices.
96
+
97
+ ---
98
+
99
+ ## Methodological caveats to carry
100
+
101
+ 1. **Comparability is bounded by setup.** The site flags when two scores under the same benchmark are not directly comparable — respect those flags in any ranking or meta-analysis.
102
+ 2. **Coverage ≠ quality.** Many results with weak documentation can look like "good coverage." Weight by the signals.
103
+ 3. **The corpus reflects what was reported, not all that exists.** Undisclosed evaluations are absent by definition.
104
+ 4. **Pin a snapshot.** Cite `ec/models/...` identifiers plus the snapshot date so your analysis is reproducible.
105
+
106
+ ➡️ Related: [Policymakers](policymakers.md) (governance framing) · [Quickstart](quickstart.md).
content/tutorials/general-public.md ADDED
@@ -0,0 +1,97 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Evaluation Cards — A Guide for Everyone
2
+
3
+ *Plain-language: what an AI "benchmark score" really means, and how to read these cards.*
4
+
5
+ You don't need a technical background for this guide. If you've seen headlines like *"New AI model scores 90% on a reasoning test!"* and wondered what that actually means, you're in the right place.
6
+
7
+ ---
8
+
9
+ ## What is this website?
10
+
11
+ **Evaluation Cards** is like a nutrition label for AI model test results.
12
+
13
+ When companies build AI models, they run them through standardized tests called **benchmarks** (think: a standardized exam for AI). They then publish scores. But a score by itself — "92%" — leaves out a lot: Who gave the test? Under what conditions? Can anyone else get the same result? Were important topics even tested?
14
+
15
+ Evaluation Cards collects these scores from across the industry and, crucially, shows you **what's missing** — so a polished number doesn't get mistaken for the full story.
16
+
17
+ > 🖼️ **Screenshot — `01-home-overview.png`**
18
+ > *What to capture:* The homepage showing the totals (thousands of models and results).
19
+
20
+ ---
21
+
22
+ ## Why a single score can be misleading
23
+
24
+ Imagine a student says "I got 95% on the exam." Reasonable follow-ups:
25
+
26
+ - *Which* exam? (An easy one or a hard one?)
27
+ - Did they grade it **themselves**, or did an independent teacher?
28
+ - Could someone else **re-take it under the same conditions** and get a similar result?
29
+ - Did the exam even cover the topics you care about?
30
+
31
+ These are exactly the questions Evaluation Cards helps you ask about AI models. A high score with no answers to these questions is just a number.
32
+
33
+ ---
34
+
35
+ ## The four things to check (the "signals")
36
+
37
+ Every result is rated on four simple ideas. You don't need the math — just the gist.
38
+
39
+ > 🖼️ **Screenshot — `03-home-signals.png`**
40
+ > *What to capture:* The four signal cards on the homepage.
41
+
42
+ | Signal | In plain words |
43
+ |---|---|
44
+ | 🔁 **Reproducibility** | Could someone else repeat this test and get the same result? If the details are secret, the answer is "we can't tell." |
45
+ | 📋 **Completeness** | Did they test the things that matter — not just the flattering stuff, but also safety and fairness? |
46
+ | 👤 **Provenance** | Who ran the test — the **company that made the model**, or an **independent group**? |
47
+ | ⚖️ **Comparability** | Can you fairly compare this model's score to another model's? (Sometimes it's apples vs. oranges.) |
48
+
49
+ **The big one for everyday readers: Provenance.** A company grading its own homework isn't *wrong*, but it isn't the same as an independent referee. The site always shows you which is which.
50
+
51
+ ---
52
+
53
+ ## How to read a model's "card"
54
+
55
+ Let's walk through one.
56
+
57
+ **Step 1 — Find a model.** Click **Models** in the menu and pick one you've heard of.
58
+
59
+ > 🖼️ **Screenshot — `09-models-index.png`**
60
+ > *What to capture:* The Models list page.
61
+
62
+ **Step 2 — Open its card.** Each model gets an "Evaluation Card."
63
+
64
+ > 🖼️ **Screenshot — `13-card-summary-full.png`**
65
+ > *What to capture:* A full model card in **Summary View**.
66
+
67
+ **Step 3 — Look for the "Documented" number.** Near the top you'll see something like **"36% documented."** Higher means more of the test details were shared. A low number isn't a scandal — it's just telling you *"take these scores with a grain of salt; a lot wasn't disclosed."*
68
+
69
+ > 🖼️ **Screenshot — `14-card-summary-top.png`**
70
+ > *What to capture:* The top of a model card with the DOCUMENTED percentage.
71
+
72
+ **Step 4 — See who did the testing.** Scroll to **"Who reports what."** A simple chart splits results into the **company's own** results vs **independent** ones.
73
+
74
+ > 🖼️ **Screenshot — `17-card-who-reports.png`**
75
+ > *What to capture:* The "Who reports what" chart (company vs. independent).
76
+
77
+ That's it. You can stop there and already read these results more wisely than most headlines do.
78
+
79
+ ---
80
+
81
+ ## What this site is *not*
82
+
83
+ - ❌ It's **not** a "best AI" leaderboard. It won't crown a winner.
84
+ - ❌ It **won't** tell you a model is "safe" — only how thoroughly (and by whom) it was tested.
85
+ - ❌ Blanks are **not** zeros. A blank means "nobody reported this," not "the model failed."
86
+
87
+ ---
88
+
89
+ ## Three takeaways
90
+
91
+ 1. **A score is a claim, not a guarantee.** Always ask who measured it and how.
92
+ 2. **Independent results carry more weight** than a company testing its own product.
93
+ 3. **What's missing matters.** If safety was never tested, the absence is part of the story.
94
+
95
+ That's the whole idea: not "which AI is best," but **"how much should we trust what we're being told about it?"**
96
+
97
+ ➡️ Curious for more? The [Quickstart](quickstart.md) goes a little deeper without getting technical.
content/tutorials/get-verified.md ADDED
@@ -0,0 +1,12 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Get a verified checkmark
2
+
3
+ *How to have your evaluation results show up as verified on Evaluation Cards.*
4
+
5
+ ---
6
+
7
+ Submit your evaluation data through a Hugging Face account associated with your organisation's HF org, and we'll mark your results with a **verified checkmark** — a signal to readers that the numbers come straight from the source.
8
+
9
+ We're calling on **all model developers and evaluators** to send their data this way. The more results that arrive verified and in a common format, the more of the corpus can be compared apples to apples.
10
+
11
+ > 🖼️ **Screenshot — `verified-checkmark.png`**
12
+ > *What to capture:* A verified result on a model page showing the checkmark badge, with its tooltip open explaining that the data was submitted through the organisation's verified Hugging Face account.
content/tutorials/how-signals-are-computed.md ADDED
@@ -0,0 +1,145 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # How the four signals are computed
2
+
3
+ *The technical companion to the four interpretive signals. This formalizes how each one is calculated, the fields it depends on, and how it rolls up across the corpus. Adapted from Appendix H.1 of the paper.*
4
+
5
+ > **See also:** the [About page](/about#four-interpretive-signals) explains what each signal means in plain language. This page is the precise definition behind it.
6
+
7
+ ---
8
+
9
+ ## The result triple
10
+
11
+ Every signal is computed over a **result triple** $r = (m, b, \mu)$:
12
+
13
+ - $m$ — a canonical model identifier,
14
+ - $b$ — a metric-path through the rollout hierarchy (family → composite → benchmark → split),
15
+ - $\mu$ — a metric.
16
+
17
+ $R$ is the set of all such triples in the corpus, and $B$ the set of canonical benchmarks. For any field $f$ and triple $r$:
18
+
19
+ $$
20
+ \mathrm{pop}(f, r) =
21
+ \begin{cases}
22
+ 1 & \text{if } f \text{ is populated in the record for } r, \\
23
+ 0 & \text{otherwise,}
24
+ \end{cases}
25
+ $$
26
+
27
+ and $\mathrm{pop}(f, b)$ is defined analogously for a benchmark $b$ and its Auto-BenchmarkCards record.
28
+
29
+ ## Reproducibility
30
+
31
+ **In plain terms.** For each result, we check whether the small set of fields needed to re-run the evaluation are present. If any are missing, we flag the result.
32
+
33
+ The minimal reproducibility sub-schema is:
34
+
35
+ $$
36
+ F_{\mathrm{repro}} = \{\, \texttt{temperature},\ \texttt{max\_tokens} \,\}.
37
+ $$
38
+
39
+ For **agentic** evaluations, $F_{\mathrm{repro}}$ is extended with $\texttt{harness}$, $\texttt{eval\_plan}$, and $\texttt{eval\_limits}$.
40
+
41
+ A result $r$ is flagged as a reproducibility gap if **any** required field is missing:
42
+
43
+ $$
44
+ G_{\mathrm{repro}}(r) = 1 - \prod_{f \in F_{\mathrm{repro}}} \mathrm{pop}(f, r).
45
+ $$
46
+
47
+ That is, $G_{\mathrm{repro}}(r) = 0$ only when every field in $F_{\mathrm{repro}}$ is populated. The interface lists the specific missing fields, $\{\, f \in F_{\mathrm{repro}} : \mathrm{pop}(f, r) = 0 \,\}$.
48
+
49
+ Corpus-level reproducibility is the share of flagged triples, and per-field reporting uses the missingness rate:
50
+
51
+ $$
52
+ \bar{G}_{\mathrm{repro}} = \frac{1}{|R|} \sum_{r \in R} G_{\mathrm{repro}}(r),
53
+ \qquad
54
+ \bar{m}(f) = 1 - \frac{1}{|R|} \sum_{r \in R} \mathrm{pop}(f, r),\quad f \in F_{\mathrm{repro}}.
55
+ $$
56
+
57
+ ## Reporting completeness
58
+
59
+ **In plain terms.** For each benchmark, we count how many of the 28 schema fields are populated. Present-or-absent fields score 0 or 1; fields that contain sub-items score the fraction of sub-items populated. The completeness score is the average across all 28 fields.
60
+
61
+ Let $F = \{ f_1, \dots, f_N \}$ be the operationalized schema with $N = 28$ fields, ingested from Auto-BenchmarkCards and EEE plus the reserved Evaluation Cards fields. Each field has a coverage type $\tau(f) \in \{ \text{full}, \text{reserved}, \text{partial} \}$, and the per-field score $s(f, b) \in [0, 1]$ is:
62
+
63
+ $$
64
+ s(f, b) =
65
+ \begin{cases}
66
+ \mathrm{pop}(f, b) & \text{if } \tau(f) \in \{ \text{full}, \text{reserved} \}, \\[1.2em]
67
+ \dfrac{1}{|\mathrm{sub}(f)|} \displaystyle\sum_{f' \in \mathrm{sub}(f)} \mathrm{pop}(f', b) & \text{if } \tau(f) = \text{partial,}
68
+ \end{cases}
69
+ $$
70
+
71
+ where $\mathrm{sub}(f)$ is the set of sub-items under a partial-coverage field. For example, a partial field with 4 sub-items, 2 of which are populated, scores $0.5$.
72
+
73
+ The completeness score for a benchmark is the unweighted mean across fields:
74
+
75
+ $$
76
+ C(b) = \frac{1}{N} \sum_{f \in F} s(f, b) = \frac{1}{28} \sum_{f \in F} s(f, b).
77
+ $$
78
+
79
+ The interface surfaces $C(b)$ alongside the count of fully missing fields, $|\{\, f \in F : s(f, b) = 0 \,\}|$. Across the corpus we report the median per-benchmark completeness, $\mathrm{median}_{b \in B}\, C(b)$, and per-field population rates, $\bar{p}(f) = \frac{1}{|B|} \sum_{b \in B} s(f, b)$.
80
+
81
+ Completeness and reproducibility are distinct: $F_{\mathrm{repro}} \subset F$, so a result with no reproducibility gap may still have low completeness.
82
+
83
+ ## Provenance
84
+
85
+ **In plain terms.** For each reported score, we surface three things: who reported it (first-party, third-party, or collaborative), whether anyone else also reported the same score, and any risk categories associated with the benchmark.
86
+
87
+ Let $\rho(r) \in \{ \texttt{first\_party}, \texttt{third\_party}, \texttt{collaborative} \}$ be the evaluator relationship for triple $r$. For a triple $(m, b, \mu)$, the set of records reporting it is $R(m, b, \mu) = \{ r \in R : r = (m, b, \mu) \}$.
88
+
89
+ A score is **first-party-only** if every report comes from the model developer:
90
+
91
+ $$
92
+ \mathrm{FPO}(m, b, \mu) =
93
+ \begin{cases}
94
+ 1 & \text{if } \rho(r) = \texttt{first\_party} \text{ for all } r \in R(m, b, \mu), \\
95
+ 0 & \text{otherwise.}
96
+ \end{cases}
97
+ $$
98
+
99
+ The multi-party indicator is $\mathrm{MP}(m, b, \mu) = 1$ when $|R(m, b, \mu)| > 1$, and $0$ otherwise. Risk annotations are propagated from the Auto-BenchmarkCards risk-mapping component: each benchmark $b$ carries a set of risk categories $K(b)$. These are shown as attention cues in the interface and do **not** enter a numerical score.
100
+
101
+ ## Comparability
102
+
103
+ **In plain terms.** For each $(m, b, \mu)$ triple with at least two reports, we check whether reported scores differ by more than 5% of the metric's range. We do this two ways — across setups for the same party (variant divergence) and across different parties (cross-party divergence). Either one triggers a flag.
104
+
105
+ Let $[\mu_{\min}, \mu_{\max}]$ be the metric's native scale and $\theta = 0.05$ the divergence threshold.
106
+
107
+ **Variant divergence.** For a triple with multiple reported setups (differing in fields such as $\texttt{max\_tokens}$, tool configuration, or agentic scaffolding), let $V(m, b, \mu)$ be the set of distinct variants and $\sigma(v)$ the score under variant $v$. It is flagged when the spread exceeds $\theta$:
108
+
109
+ $$
110
+ D_{\mathrm{var}}(m, b, \mu) =
111
+ \begin{cases}
112
+ 1 & \text{if } \dfrac{\max_v \sigma(v) - \min_v \sigma(v)}{\mu_{\max} - \mu_{\min}} > \theta, \\[1.4em]
113
+ 0 & \text{otherwise.}
114
+ \end{cases}
115
+ $$
116
+
117
+ The differing fields are surfaced as the comparability annotation.
118
+
119
+ **Cross-party divergence.** Let $P(m, b, \mu) = \{ \rho(r) : r \in R(m, b, \mu) \}$ be the set of reporting parties and $\sigma(p)$ the score reported by party $p$ (averaged across variants within a party if needed). It is flagged when more than one party reports the triple and the spread exceeds $\theta$:
120
+
121
+ $$
122
+ D_{\mathrm{cp}}(m, b, \mu) =
123
+ \begin{cases}
124
+ 1 & \text{if } |P(m, b, \mu)| > 1 \text{ and } \dfrac{\max_p \sigma(p) - \min_p \sigma(p)}{\mu_{\max} - \mu_{\min}} > \theta, \\[1.4em]
125
+ 0 & \text{otherwise.}
126
+ \end{cases}
127
+ $$
128
+
129
+ The underlying setup differences across parties are rendered alongside the divergence.
130
+
131
+ **Combined flag.** The overall comparability signal is the maximum of the two:
132
+
133
+ $$
134
+ D_{\mathrm{comp}}(m, b, \mu) = \max\big(\, D_{\mathrm{var}}(m, b, \mu),\ D_{\mathrm{cp}}(m, b, \mu) \,\big).
135
+ $$
136
+
137
+ The threshold $\theta = 0.05$ is applied uniformly across metrics; metric-specific thresholds are a candidate extension.
138
+
139
+ ---
140
+
141
+ ## One thing to keep in mind
142
+
143
+ None of these signals is a grade. Evaluation Cards assigns no letter grades, pass/fail thresholds, or completeness rankings — when a field is omitted, it lowers the completeness score, may trip the reproducibility, provenance, or comparability signals, and is shown to readers directly. The intent is to make reporting choices visible, not to enforce a particular reporting standard.
144
+
145
+ *Adapted from [Appendix H.1, "Computation of Interpretive Signals"](https://arxiv.org/abs/2606.09809) of the paper.*
content/tutorials/journalists.md ADDED
@@ -0,0 +1,91 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Evaluation Cards for Journalists
2
+
3
+ *How to source AI benchmark claims accurately, cite them defensibly, and avoid the common overclaiming traps.*
4
+
5
+ > **Prerequisite:** the [Quickstart](quickstart.md) (~10 min) covers the four signals and the snapshot model.
6
+
7
+ ---
8
+
9
+ ## Why this is a reporting tool, not just a database
10
+
11
+ AI companies publish benchmark numbers constantly, often in launch posts engineered for headlines. Evaluation Cards lets you do three things fast:
12
+
13
+ 1. **Verify** whether a claimed score is independently corroborated or self-reported.
14
+ 2. **Contextualize** a number with how well-documented and comparable it actually is.
15
+ 3. **Cite** a stable, dated source instead of a marketing page.
16
+
17
+ The project's framing is useful for reporters: a published score is a **claim**, and an undisclosed detail is **a claim deliberately not made**. Your job is to report which is which.
18
+
19
+ > 🖼️ **Screenshot — `01-home-overview.png`**
20
+ > *What to capture:* The homepage with the corpus snapshot.
21
+
22
+ ---
23
+
24
+ ## The 3-minute fact-check
25
+
26
+ A company claims "Model X leads on benchmark Y." Before you repeat it:
27
+
28
+ **1. Find the model card.** Models → search.
29
+
30
+ > 🖼️ **Screenshot — `09-models-index.png`**
31
+ > *What to capture:* The Models index.
32
+
33
+ **2. Is the claim first-party or third-party?** Open **§3 "Who reports what."** If the impressive number is the company's *own* result with no independent corroboration, say so in your piece.
34
+
35
+ > 🖼️ **Screenshot — `17-card-who-reports.png`**
36
+ > *What to capture:* The §3 first-party vs third-party breakdown.
37
+
38
+ **3. How documented is it?** The **`DOCUMENTED`** badge (e.g. "36% — 14/39 reported") tells you how much of the record is fully specified. A flashy score with weak documentation is a weak claim — worth a caveat.
39
+
40
+ > 🖼️ **Screenshot — `14-card-summary-top.png`**
41
+ > *What to capture:* The card header with the DOCUMENTED badge.
42
+
43
+ **4. Is the comparison even valid?** The **Comparability** signal flags when two scores on the "same" benchmark used different slices, metrics, or units. "Beats the competition" headlines frequently fail this test.
44
+
45
+ **5. Was the relevant area tested at all?** Check **§2 Benchmark coverage**. If a safety/robustness claim has no corresponding evaluation, the absence is your story.
46
+
47
+ > 🖼️ **Screenshot — `16-card-coverage.png`**
48
+ > *What to capture:* The §2 Benchmark coverage section.
49
+
50
+ ---
51
+
52
+ ## Finding who reported what (sourcing)
53
+
54
+ Every score is attributed to its source document and reporting organization. Use the **Evaluations** page to explore a benchmark family and see which organizations reported results, and the model card's §4 to see the source harness behind each number.
55
+
56
+ > 🖼️ **Screenshot — `05-evals-index.png`**
57
+ > *What to capture:* The Evaluations index (families with categories, benchmark and result counts).
58
+
59
+ > 🖼️ **Screenshot — `08-evals-family-expanded.png`**
60
+ > *What to capture:* A single benchmark family page (e.g. `/evals?family=artificial-analysis`).
61
+
62
+ This lets you write "according to [organization], reported in [source]" rather than "the company says."
63
+
64
+ ---
65
+
66
+ ## Citing it correctly
67
+
68
+ - **Cite the snapshot.** Every page is dated; the corpus is versioned and not retroactively edited. Write: *"per Evaluation Cards, snapshot [date]."*
69
+ - **Use the stable identifier.** Each model has an ID like `ec/models/anthropic/claude-opus-4.7`. Link the card directly.
70
+ - **Attribute the evaluator,** not just the model: *"a third-party result reported by [org]"* vs *"the developer's own reported result."*
71
+ - **Quote the number with its context** — the slice/metric and whether it's directly comparable.
72
+
73
+ ---
74
+
75
+ ## Overclaiming traps to avoid
76
+
77
+ | Trap | Better framing |
78
+ |---|---|
79
+ | "Model X is the best/safest." | "Model X reports the highest *self-reported* score on [benchmark]; there are no independent results for this in the corpus." |
80
+ | Reporting a blank as a failure. | A blank means *not reported*, not zero. Say "no evaluation was reported." |
81
+ | "Model A beats Model B." | Check Comparability first — different setups can make the comparison invalid. |
82
+ | Citing a launch blog as the source. | Cite the attributed evaluation + reporting organization + snapshot date. |
83
+ | Treating one snapshot as permanent. | Numbers change; date your claim. |
84
+
85
+ ---
86
+
87
+ ## A note on independence
88
+
89
+ The most defensible AI-performance reporting distinguishes the developer's own numbers from independent ones. The **§3 "Who reports what"** view makes that distinction in one glance — and a category that is *entirely first-party* is exactly where a careful reporter adds "self-reported, not independently verified."
90
+
91
+ ➡️ Related: [Policymakers](policymakers.md) (governance framing) · [General public](general-public.md) (plain-language explainer).
content/tutorials/model-developers.md ADDED
@@ -0,0 +1,127 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Evaluation Cards for Model Developers
2
+
3
+ *How your model appears in the corpus, how to read what's documented vs. missing, and how to make your evaluation reporting stronger.*
4
+
5
+ > **Prerequisite:** the [Quickstart](quickstart.md) (~10 min) covers the four signals, the five-level hierarchy, and the snapshot model.
6
+
7
+ ---
8
+
9
+ ## Why you should care how your model is carded
10
+
11
+ Whatever you publish about your model's evaluations, Evaluation Cards re-presents it as a structured record alongside everyone else's — and, crucially, shows **what you did not disclose**. The project treats a published score as a **claim** and an undisclosed detail as **a claim deliberately not made** (not an error). That means your card is, in effect, a public read on how *legible* and *verifiable* your reporting is.
12
+
13
+ A high benchmark number with weak signals reads as a weak claim. The good news: most of the gaps are cheap to close, and this guide is organized as a checklist for doing exactly that.
14
+
15
+ > 🖼️ **Screenshot — `01-home-overview.png`**
16
+ > *What to capture:* The homepage with the corpus snapshot and the four signals.
17
+
18
+ ---
19
+
20
+ ## Step 1 — Find your model (and your org)
21
+
22
+ - **Models view** (`/models`): search for your model, filter by parameter range, and open its card.
23
+
24
+ > 🖼️ **Screenshot — `09-models-index.png`**
25
+ > *What to capture:* The Models index list.
26
+
27
+ - **Developers view**: toggle **Models → Developers** on the same page to see your organization's footprint across all its models.
28
+
29
+ > 🖼️ **Screenshot — `22-developers-view.png`**
30
+ > *What to capture:* The `/models` page with the **Developers** toggle active.
31
+
32
+ ---
33
+
34
+ ## Step 2 — Read your card honestly
35
+
36
+ Open your model's card in **Summary View**, then switch to **Researcher View** to see the per-result detail others will scrutinize.
37
+
38
+ > 🖼️ **Screenshot — `13-card-summary-full.png`**
39
+ > *What to capture:* A full model card in Summary View.
40
+
41
+ > 🖼️ **Screenshot — `19-card-researcher-full.png`**
42
+ > *What to capture:* The same card after clicking **Researcher View**.
43
+
44
+ Three things to look at first:
45
+
46
+ 1. **The `DOCUMENTED` badge** (e.g. "36% — 14 / 39 reported"). This is the headline read on your reporting hygiene: how much of your reported record is fully specified. Treat a low number as a backlog, not a verdict.
47
+
48
+ > 🖼️ **Screenshot — `14-card-summary-top.png`**
49
+ > *What to capture:* The card header with the DOCUMENTED badge.
50
+
51
+ 2. **§1 Identification** — confirm the basics are right: model name, developer, release date, modalities, system ID. Errors here propagate everywhere.
52
+
53
+ > 🖼️ **Screenshot — `15-card-identification.png`**
54
+ > *What to capture:* The §1 Identification block.
55
+
56
+ 3. **§2 Benchmark coverage** — what categories are present, and where the **slice spread** is. Gaps here are visible to everyone reading your card.
57
+
58
+ > 🖼️ **Screenshot — `16-card-coverage.png`**
59
+ > *What to capture:* The §2 Benchmark coverage section.
60
+
61
+ ---
62
+
63
+ ## Step 3 — Work the four signals as a reporting checklist
64
+
65
+ Each signal maps to concrete, mostly low-cost actions.
66
+
67
+ ### 🔁 Reproducibility — *make it re-runnable*
68
+ Disclose, per result: **setup variants, prompts, decoding parameters, harness name + version, random seeds, and code/artifacts**. Corpus-wide only ~3% of scores have complete setup documentation — so even modest disclosure stands out.
69
+
70
+ - ✅ Publish the exact harness + version (e.g. the eval framework and commit).
71
+ - ✅ State decoding settings (temperature, top-p, max tokens) and seeds.
72
+ - ✅ Link runnable code or a config, not just a number.
73
+
74
+ ### 📋 Completeness — *cover the categories that matter*
75
+ Completeness is judged relative to expectations for your model class. A strong **capability** record that is silent on **safety**, **robustness**, or **fairness** reads as incomplete.
76
+
77
+ - ✅ Report beyond the flattering capability benchmarks.
78
+ - ✅ If a category is intentionally out of scope, the absence will still show — consider documenting why.
79
+
80
+ ### 👤 Provenance & Risk — *invite independent evaluation*
81
+ Your card splits results into **first-party** (your own) vs **third-party** (independent), and maps results to **IBM Risk Atlas** risk domains. A category that is **entirely first-party** is a visible blind spot: impressive, but uncorroborated.
82
+
83
+ > 🖼️ **Screenshot — `17-card-who-reports.png`**
84
+ > *What to capture:* The §3 "Who reports what" first-party vs third-party breakdown.
85
+
86
+ - ✅ Encourage / enable third-party evaluation, especially for safety-relevant claims.
87
+ - ✅ Don't expect self-reported numbers alone to carry weight with careful readers.
88
+
89
+ ### ⚖️ Comparability — *report so your scores can be compared*
90
+ The site flags when two scores on the same benchmark used different slices, metric variants, or units — which invalidates direct comparison.
91
+
92
+ > 🖼️ **Screenshot — `18-card-metrics.png`**
93
+ > *What to capture:* The §4 Reported metrics section with benchmark charts.
94
+
95
+ - ✅ Use the standard slices and metric definitions for each benchmark.
96
+ - ✅ State units explicitly; don't silently switch metric variants.
97
+ - ✅ Use the **Evaluations** page to see how others report the same benchmark family.
98
+
99
+ > 🖼️ **Screenshot — `08-evals-family-expanded.png`**
100
+ > *What to capture:* A benchmark family detail page (e.g. `/evals?family=artificial-analysis`).
101
+
102
+ ---
103
+
104
+ ## Step 4 — Corrections and snapshots
105
+
106
+ The corpus follows **snapshot discipline**: no retroactive edits, only versioned corrections. Practically:
107
+
108
+ - A number you published is attributed to its source document and tied to a dated snapshot — it won't be silently rewritten.
109
+ - If something is genuinely wrong or missing, the path is a **correction in a future snapshot**, not an edit-in-place. Keep your own source documents stable and clearly dated so they can be cited cleanly.
110
+ - Because nothing is imputed, the fastest way to improve your card is simply to **report more, and report it precisely** — the corpus will reflect it on the next snapshot.
111
+
112
+ ---
113
+
114
+ ## A pre-launch checklist
115
+
116
+ Before your next model announcement, check that each headline benchmark claim ships with:
117
+
118
+ - [ ] Harness name + version, and a link to runnable code/config
119
+ - [ ] Decoding settings and seeds
120
+ - [ ] The exact slice and metric (with units), matching how the benchmark is normally reported
121
+ - [ ] Coverage beyond capability — at least some safety / robustness / fairness results
122
+ - [ ] At least one path to independent (third-party) evaluation for key claims
123
+ - [ ] A stable, dated source document for every number
124
+
125
+ Closing these is what moves your `DOCUMENTED` percentage — and turns marketing numbers into claims that hold up.
126
+
127
+ ➡️ Related: [Evaluation researchers](evaluation-researchers.md) (how researchers will scrutinize your card) · [Journalists](journalists.md) (how reporters will source your claims) · [Quickstart](quickstart.md).
content/tutorials/policymakers.md ADDED
@@ -0,0 +1,101 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Evaluation Cards for Policymakers
2
+
3
+ *How to read AI evaluation evidence for governance decisions — what it supports, and what it does not.*
4
+
5
+ > **Prerequisite:** the [Quickstart](quickstart.md) explains the four signals and the snapshot model in ~10 minutes.
6
+
7
+ ---
8
+
9
+ ## The one idea to take away
10
+
11
+ When a company says "our model scored X% on a safety benchmark," that is a **claim**, not an audited fact. Evaluation Cards exists to show you the *quality of the evidence* behind such claims: who produced it, whether it can be reproduced, and whether it can be fairly compared to anyone else's number.
12
+
13
+ For policy, the headline score is rarely the decision-relevant variable. **The documentation and independence behind the score are.**
14
+
15
+ > 🖼️ **Screenshot — `01-home-overview.png`**
16
+ > *What to capture:* The homepage with the corpus snapshot and the four signals.
17
+
18
+ ---
19
+
20
+ ## What the corpus does and does not tell you
21
+
22
+ **It does:**
23
+ - Aggregate how thousands of models have been evaluated, across many independent reporting organizations.
24
+ - Make explicit *what was not disclosed* — treating undocumented setups as a measurable gap, not an oversight.
25
+ - Distinguish a developer's own results from independent third-party evaluations.
26
+
27
+ **It does not:**
28
+ - Certify that any model is "safe," "compliant," or "best." There is no ranking or seal of approval.
29
+ - Fill in missing data. A blank means "not reported," never an estimate.
30
+ - Replace an audit. It tells you how *auditable* a claim currently is.
31
+
32
+ ---
33
+
34
+ ## Reading the four signals as a governance lens
35
+
36
+ > 🖼️ **Screenshot — `04-about-full.png`**
37
+ > *What to capture:* The About / methodology page describing the four signals.
38
+
39
+ | Signal | Governance question | Why it matters for policy |
40
+ |---|---|---|
41
+ | **Reproducibility** | Could an independent party verify this claim? | A score that cannot be reproduced cannot be relied on for oversight. Corpus-wide, only ~3% of scores have complete setup documentation. |
42
+ | **Completeness** | Were the relevant risk areas evaluated at all? | A strong capability record can be silent on safety, robustness, or fairness. Absence of a result is not evidence of safety. |
43
+ | **Provenance & Risk** | Who ran the evaluation, and what real-world risk does it speak to? | Self-reported results lack independent corroboration. Results map to **IBM Risk Atlas** risk domains, connecting scores to recognized risk categories. |
44
+ | **Comparability** | Can these two models actually be compared on this benchmark? | "Model A beats Model B" is often invalid if they used different setups. The site flags when a comparison is not legitimate. |
45
+
46
+ ---
47
+
48
+ ## First-party vs third-party: the independence check
49
+
50
+ The single most useful view for governance is **§3 "Who reports what"** on any model card. It splits a model's results into:
51
+
52
+ - **First-party** — produced by the model's own developer.
53
+ - **Third-party** — produced independently.
54
+
55
+ > 🖼️ **Screenshot — `17-card-who-reports.png`**
56
+ > *What to capture:* The §3 "Who reports what" first-party vs third-party breakdown on a model card.
57
+
58
+ In the captured example, a flagship model's record was **31% first-party / 69% third-party**, and some categories were *entirely* third-party or entirely first-party. A category with **no independent evaluations** is a place where policy should not lean on the numbers without seeking corroboration.
59
+
60
+ ---
61
+
62
+ ## A short workflow for a policy question
63
+
64
+ Suppose you need to assess the evidence base for a specific model.
65
+
66
+ 1. **Open its card.** Models → search the model.
67
+ > 🖼️ **Screenshot — `09-models-index.png`**
68
+ > *What to capture:* The Models index list.
69
+
70
+ 2. **Read the `DOCUMENTED` badge** (e.g. "36% — 14 / 39 reported"). This is, at a glance, how much of the record is fully documented. Treat a low number as "claims that are hard to verify."
71
+
72
+ > 🖼️ **Screenshot — `14-card-summary-top.png`**
73
+ > *What to capture:* The top of a model card showing the DOCUMENTED badge and the summary paragraph.
74
+
75
+ 3. **Check §3 (Who reports what)** for independence, by category.
76
+
77
+ 4. **Check §2 (Benchmark coverage)** for *what risk areas were evaluated at all.*
78
+ > 🖼️ **Screenshot — `16-card-coverage.png`**
79
+ > *What to capture:* The §2 Benchmark coverage section.
80
+
81
+ 5. **Note the snapshot date.** The corpus is versioned; cite the date.
82
+
83
+ ---
84
+
85
+ ## What you can responsibly say
86
+
87
+ ✅ *"As of the [snapshot date] corpus, X% of this model's reported results are fully documented, and Y% come from independent evaluators."*
88
+
89
+ ✅ *"There are no reported [safety / robustness / fairness] evaluations for this model in the corpus."* (Absence is itself a finding.)
90
+
91
+ ❌ *"This model is the safest"* / *"This model ranks #1."* The corpus does not certify or rank.
92
+
93
+ ❌ Treating a missing value as a low score, or a high score with weak signals as a strong claim.
94
+
95
+ ---
96
+
97
+ ## Why the framing matters
98
+
99
+ Evaluation Cards deliberately treats an undisclosed detail as **a claim intentionally not made** — not an error. For policy this is the useful posture: it shifts the question from *"what's the number?"* to *"how much can we trust and verify this number, and who stands behind it?"* — which is the question governance actually needs answered.
100
+
101
+ ➡️ Related: [Journalists](journalists.md) (sourcing claims responsibly) · [Evaluation researchers](evaluation-researchers.md) (deeper methodology).
content/tutorials/quickstart.md ADDED
@@ -0,0 +1,99 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Evaluation Cards — Quickstart
2
+
3
+ *A stakeholder-agnostic guide to getting started. ~10 minutes.*
4
+
5
+ > 🖼️ **Screenshot — `01-home-overview.png`**
6
+ > *What to capture:* The full homepage at <https://evalcards.evalevalai.com> showing the headline, the **Corpus snapshot**, and the four interpretive signals.
7
+
8
+ ---
9
+
10
+ ## What Evaluation Cards is
11
+
12
+ **Evaluation Cards** is a reporting layer over AI model evaluations, built by the [EvalEval Coalition](https://evalcards.evalevalai.com/about). It collects how AI models are evaluated across many benchmarks and reporting organizations, and — just as importantly — shows **what was left undocumented**.
13
+
14
+ A benchmark score on its own ("Model X scores 87% on MMLU") tells you very little. Evaluation Cards puts each score in context: *who* ran the evaluation, *how* it was set up, *whether* it can be reproduced, and *whether* it can be fairly compared to another score. The project treats every published evaluation as a **claim**, and every undisclosed detail as **a claim deliberately not made** — neither is treated as an error.
15
+
16
+ At a glance (snapshot of June 2026), the corpus tracks:
17
+
18
+ | | |
19
+ |---|---|
20
+ | **5,816** models | **101,955** reported results |
21
+ | **31** reporting organizations | **820** model developers |
22
+ | **57** benchmark families | **638** single benchmarks |
23
+
24
+ > The corpus is **versioned by snapshot**. Every page shows a snapshot date. Numbers above will drift as the corpus grows — always cite the snapshot you saw.
25
+
26
+ ---
27
+
28
+ ## The four interpretive signals
29
+
30
+ Every record is assessed against four signals. These are the heart of the site — learn to read them and the rest follows.
31
+
32
+ > 🖼️ **Screenshot — `03-home-signals.png`**
33
+ > *What to capture:* The "Interpretive signals" section on the homepage (the four cards: Reproducibility, Completeness, Provenance, Comparability).
34
+
35
+ | Signal | Question it answers | What a low score means |
36
+ |---|---|---|
37
+ | **R — Reproducibility** | Could a third party re-run this evaluation? | Prompts, decoding settings, harness version, seeds, or code are undisclosed. |
38
+ | **C — Completeness** | Does the record meet normal reporting expectations for this kind of model? | Whole categories (e.g. safety, robustness, fairness) may be missing. |
39
+ | **P — Provenance & Risk** | Who ran it, and what real-world property does it measure? | Distinguishes **first-party** (the developer) from **third-party** (independent) evaluators. |
40
+ | **X — Comparability** | Can two scores on the same benchmark be put side by side? | Different slices, metric variants, or units make a direct ranking invalid. |
41
+
42
+ A high benchmark score with weak signals is still a weak claim. The signals are how you tell a well-documented result from a number with no paper trail.
43
+
44
+ ---
45
+
46
+ ## The five-level hierarchy
47
+
48
+ Scores resolve through an explicit pathway, so any headline number can be drilled down to the evidence behind it:
49
+
50
+ ```
51
+ Family → Composite → Single Benchmark → Slice → Metric
52
+ ```
53
+
54
+ For example: *MMLU (family) → MMLU-Pro (composite) → a single subject → a language/subset slice → accuracy (metric)*. When you see an aggregate claim, you can always click down to the specific metric supporting it.
55
+
56
+ ---
57
+
58
+ ## Getting around: the four pages
59
+
60
+ > 🖼️ **Screenshot — `02-home-hero.png`**
61
+ > *What to capture:* The top navigation bar (Overview · Models · Evaluations · About).
62
+
63
+ 1. **Overview** (`/`) — the corpus snapshot, the signals explained, and featured benchmark families. Start here.
64
+ 2. **Models** (`/models`) — every indexed model. Filter by parameter size, switch between **Models** and **Developers** views, and select up to four models to compare.
65
+ 3. **Evaluations** (`/evals`) — benchmarks grouped into **families**, filterable by interaction style (agent / non-agent) and ~17 categories (Mathematics, Safety, Software Engineering, …).
66
+ 4. **About** (`/about`) — the methodology: how the signals are computed and the principles behind the corpus.
67
+
68
+ ---
69
+
70
+ ## Your first 5 minutes
71
+
72
+ 1. **Open a model card.** Go to **Models**, click any model (e.g. *Claude Opus 4.7*). This is an *Evaluation Card*.
73
+
74
+ > 🖼️ **Screenshot — `13-card-summary-full.png`**
75
+ > *What to capture:* A full model Evaluation Card in **Summary View** (e.g. `/models/anthropic/claude-opus-4.7`).
76
+
77
+ 2. **Read the `DOCUMENTED` badge.** Near the top, a percentage (e.g. "36% — 14 / 39 reported") tells you how much of this model's reported record is fully documented. Low is common; that's the point.
78
+
79
+ 3. **Check "Who reports what" (§3).** A donut and per-category bars split results into **first-party** (the developer's own numbers) vs **third-party** (independent). This is your fastest read on how independent the evidence is.
80
+
81
+ > 🖼️ **Screenshot — `17-card-who-reports.png`**
82
+ > *What to capture:* The §3 "Who reports what" section of a model card (first-party vs third-party breakdown).
83
+
84
+ 4. **Toggle Summary View → Researcher View.** The top-right toggle exposes the underlying per-result detail. Summary is for orientation; Researcher is for digging in.
85
+
86
+ > 🖼️ **Screenshot — `19-card-researcher-full.png`**
87
+ > *What to capture:* The same model card after clicking **Researcher View**.
88
+
89
+ 5. **Note the snapshot date** before you cite anything.
90
+
91
+ ---
92
+
93
+ ## Three things to remember
94
+
95
+ - **A score is a claim, not a fact.** Read the signals before trusting the number.
96
+ - **First-party ≠ third-party.** Always check who produced a result.
97
+ - **Cite the snapshot.** The corpus is versioned; numbers change.
98
+
99
+ ➡️ **Next:** pick the guide for your role — [Evaluation researchers](evaluation-researchers.md) · [Policymakers](policymakers.md) · [General public](general-public.md) · [Journalists](journalists.md).
lib/tutorials.ts ADDED
@@ -0,0 +1,183 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import "server-only"
2
+
3
+ import fs from "node:fs"
4
+ import path from "node:path"
5
+
6
+ const TUTORIALS_DIR = path.join(process.cwd(), "content", "tutorials")
7
+ const SCREENSHOTS_DIR = path.join(process.cwd(), "public", "tutorials", "screenshots")
8
+
9
+ export type TutorialCategory = "guide" | "doc"
10
+
11
+ export interface TutorialMeta {
12
+ slug: string
13
+ title: string
14
+ category: TutorialCategory
15
+ /** Short "who it's for" (guides) or topic (docs) line. */
16
+ audience: string
17
+ /** One-sentence description of the focus. */
18
+ blurb: string
19
+ }
20
+
21
+ /**
22
+ * Ordered guide catalogue. Quickstart is stakeholder-agnostic and listed
23
+ * first; the rest are the per-stakeholder guides. Copy mirrors the table in
24
+ * the source tutorials README so the hub reads consistently with the guides.
25
+ */
26
+ export const TUTORIALS: TutorialMeta[] = [
27
+ {
28
+ slug: "quickstart",
29
+ title: "Quickstart",
30
+ category: "guide",
31
+ audience: "Stakeholder-agnostic · ~10 min",
32
+ blurb:
33
+ "The four signals, the five-level hierarchy, and your first five minutes on the site.",
34
+ },
35
+ {
36
+ slug: "evaluation-researchers",
37
+ title: "Evaluation researchers",
38
+ category: "guide",
39
+ audience: "Researchers auditing or comparing evaluations",
40
+ blurb:
41
+ "Researcher View, a per-section card walkthrough, rigorous signal reading, and comparability caveats.",
42
+ },
43
+ {
44
+ slug: "policymakers",
45
+ title: "Policymakers",
46
+ category: "guide",
47
+ audience: "Governance & policy",
48
+ blurb:
49
+ "What the evidence supports versus what it doesn't, independence checks, and responsible claims.",
50
+ },
51
+ {
52
+ slug: "model-developers",
53
+ title: "Model developers",
54
+ category: "guide",
55
+ audience: "Teams publishing models",
56
+ blurb:
57
+ "How your model is carded, what's documented versus missing, and a checklist to raise your signals.",
58
+ },
59
+ {
60
+ slug: "general-public",
61
+ title: "General public",
62
+ category: "guide",
63
+ audience: "Everyone",
64
+ blurb: "Plain-language: what a benchmark score means and how to read a card.",
65
+ },
66
+ {
67
+ slug: "journalists",
68
+ title: "Journalists",
69
+ category: "guide",
70
+ audience: "Reporters",
71
+ blurb: "The three-minute fact-check, sourcing, citation, and overclaiming traps.",
72
+ },
73
+ ]
74
+
75
+ /**
76
+ * Technical documentation — deeper than the stakeholder guides. Rendered from
77
+ * the same markdown pipeline and routed under /help/<slug>.
78
+ */
79
+ export const DOCS: TutorialMeta[] = [
80
+ {
81
+ slug: "how-signals-are-computed",
82
+ title: "How the four signals are computed",
83
+ category: "doc",
84
+ audience: "Signal definitions",
85
+ blurb:
86
+ "The exact computation behind reproducibility, completeness, provenance, and comparability — fields, formulas, and corpus aggregation.",
87
+ },
88
+ {
89
+ slug: "cross-post-to-hugging-face",
90
+ title: "Cross-post EEE results to Hugging Face",
91
+ category: "doc",
92
+ audience: "Contributing evaluation data",
93
+ blurb:
94
+ "Send your Every Eval Ever results to Hugging Face Community Evals — the YAML schema, the converter, and the backlink to the full EEE record.",
95
+ },
96
+ {
97
+ slug: "get-verified",
98
+ title: "Get a verified checkmark",
99
+ category: "doc",
100
+ audience: "Verification",
101
+ blurb:
102
+ "Submit your data through your organisation's Hugging Face account to have your results show up verified — our call for apples-to-apples comparison.",
103
+ },
104
+ ]
105
+
106
+ const ALL_ENTRIES = [...TUTORIALS, ...DOCS]
107
+
108
+ export function getTutorialSlugs(): string[] {
109
+ return ALL_ENTRIES.map((t) => t.slug)
110
+ }
111
+
112
+ export function getTutorialMeta(slug: string): TutorialMeta | undefined {
113
+ return ALL_ENTRIES.find((t) => t.slug === slug)
114
+ }
115
+
116
+ function listExistingScreenshots(): Set<string> {
117
+ try {
118
+ return new Set(fs.readdirSync(SCREENSHOTS_DIR))
119
+ } catch {
120
+ return new Set()
121
+ }
122
+ }
123
+
124
+ /**
125
+ * Reads a tutorial markdown file and returns it ready for rendering:
126
+ * screenshot placeholder blocks are converted into image references. Where a
127
+ * matching PNG exists in public/tutorials/screenshots it becomes a real image;
128
+ * otherwise it becomes a `placeholder:<file>` reference the renderer styles as
129
+ * a "screenshot coming" callout. Returns null if the slug has no file.
130
+ */
131
+ export function readTutorial(slug: string): string | null {
132
+ if (!getTutorialMeta(slug)) return null
133
+ const filePath = path.join(TUTORIALS_DIR, `${slug}.md`)
134
+ let raw: string
135
+ try {
136
+ raw = fs.readFileSync(filePath, "utf8")
137
+ } catch {
138
+ return null
139
+ }
140
+ return transformScreenshotBlocks(raw, listExistingScreenshots())
141
+ }
142
+
143
+ /**
144
+ * Rewrites the `> 🖼️ **Screenshot — \`file.png\`** / *What to capture:* …`
145
+ * blockquotes into markdown images. Real screenshots resolve to a public path;
146
+ * missing ones become `placeholder:` images so the renderer can style them.
147
+ */
148
+ function transformScreenshotBlocks(raw: string, existing: Set<string>): string {
149
+ const lines = raw.split("\n")
150
+ const out: string[] = []
151
+
152
+ for (let i = 0; i < lines.length; i++) {
153
+ if (!/^>\s*🖼️/.test(lines[i])) {
154
+ out.push(lines[i])
155
+ continue
156
+ }
157
+
158
+ // Collect the contiguous blockquote that starts with the screenshot marker.
159
+ const block: string[] = []
160
+ while (i < lines.length && /^>/.test(lines[i])) {
161
+ block.push(lines[i])
162
+ i++
163
+ }
164
+ i-- // the outer loop will advance past the last consumed line
165
+
166
+ const inner = block.map((l) => l.replace(/^>\s?/, "")).join("\n")
167
+ const file = inner.match(/`([^`]+\.png)`/)?.[1]
168
+ if (!file) continue // malformed marker — drop it rather than render noise
169
+
170
+ const rawCaption = inner.match(/\*What to capture:\*\s*([\s\S]+)$/)?.[1] ?? ""
171
+ const caption = rawCaption
172
+ .replace(/[*`<>]/g, "") // strip markdown emphasis / autolink / code markers
173
+ .replace(/\s+/g, " ")
174
+ .replace(/[[\]()]/g, "") // keep markdown image alt syntax intact
175
+ .trim()
176
+ const alt = caption || `Screenshot: ${file}`
177
+ const src = existing.has(file) ? `/tutorials/screenshots/${file}` : `placeholder:${file}`
178
+
179
+ out.push("", `![${alt}](${src})`, "")
180
+ }
181
+
182
+ return out.join("\n")
183
+ }
package.json CHANGED
@@ -56,6 +56,7 @@
56
  "embla-carousel-react": "8.5.1",
57
  "geist": "^1.3.1",
58
  "input-otp": "1.4.1",
 
59
  "lucide-react": "^0.454.0",
60
  "next": "15.2.8",
61
  "next-themes": "latest",
@@ -64,8 +65,12 @@
64
  "react-dom": "^19",
65
  "react-hook-form": "^7.60.0",
66
  "react-is": "^19.1.1",
 
67
  "react-resizable-panels": "^2.1.7",
68
  "recharts": "latest",
 
 
 
69
  "server-only": "^0.0.1",
70
  "sonner": "^1.7.4",
71
  "tailwind-merge": "^2.5.5",
 
56
  "embla-carousel-react": "8.5.1",
57
  "geist": "^1.3.1",
58
  "input-otp": "1.4.1",
59
+ "katex": "^0.17.0",
60
  "lucide-react": "^0.454.0",
61
  "next": "15.2.8",
62
  "next-themes": "latest",
 
65
  "react-dom": "^19",
66
  "react-hook-form": "^7.60.0",
67
  "react-is": "^19.1.1",
68
+ "react-markdown": "^10.1.0",
69
  "react-resizable-panels": "^2.1.7",
70
  "recharts": "latest",
71
+ "rehype-katex": "^7.0.1",
72
+ "remark-gfm": "^4.0.1",
73
+ "remark-math": "^6.0.0",
74
  "server-only": "^0.0.1",
75
  "sonner": "^1.7.4",
76
  "tailwind-merge": "^2.5.5",
pnpm-lock.yaml CHANGED
@@ -119,6 +119,9 @@ importers:
119
  input-otp:
120
  specifier: 1.4.1
121
  version: 1.4.1(react-dom@19.1.1(react@19.1.1))(react@19.1.1)
 
 
 
122
  lucide-react:
123
  specifier: ^0.454.0
124
  version: 0.454.0(react@19.1.1)
@@ -143,12 +146,24 @@ importers:
143
  react-is:
144
  specifier: ^19.1.1
145
  version: 19.1.1
 
 
 
146
  react-resizable-panels:
147
  specifier: ^2.1.7
148
  version: 2.1.9(react-dom@19.1.1(react@19.1.1))(react@19.1.1)
149
  recharts:
150
  specifier: latest
151
  version: 3.8.1(@types/react@19.1.10)(react-dom@19.1.1(react@19.1.1))(react-is@19.1.1)(react@19.1.1)(redux@5.0.1)
 
 
 
 
 
 
 
 
 
152
  server-only:
153
  specifier: ^0.0.1
154
  version: 0.0.1
@@ -1670,9 +1685,27 @@ packages:
1670
  '@types/d3-timer@3.0.2':
1671
  resolution: {integrity: sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==}
1672
 
 
 
 
 
 
 
1673
  '@types/estree@1.0.8':
1674
  resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==}
1675
 
 
 
 
 
 
 
 
 
 
 
 
 
1676
  '@types/node@22.17.2':
1677
  resolution: {integrity: sha512-gL6z5N9Jm9mhY+U2KXZpteb+09zyffliRkZyZOHODGATyC5B1Jt/7TzuuiLkFsSUMLbS1OLmlj/E+/3KF4Q/4w==}
1678
 
@@ -1684,12 +1717,21 @@ packages:
1684
  '@types/react@19.1.10':
1685
  resolution: {integrity: sha512-EhBeSYX0Y6ye8pNebpKrwFJq7BoQ8J5SO6NlvNwwHjSj6adXJViPQrKlsyPw7hLBLvckEMO1yxeGdR82YBBlDg==}
1686
 
 
 
 
 
 
 
1687
  '@types/use-sync-external-store@0.0.6':
1688
  resolution: {integrity: sha512-zFDAD+tlpf2r4asuHEj0XH6pY6i0g5NeAHPn+15wk3BV6JA69eERFXC1gyGThDkVa1zCyKr5jox1+2LbV/AMLg==}
1689
 
1690
  '@types/yauzl@2.10.3':
1691
  resolution: {integrity: sha512-oJoftv0LSuaDZE3Le4DbKX+KS9G36NzOeSap90UIK0yMA/NhKJhqlSGtNDORNRaIbQfzjXDrQa0ytJ6mNRGz/Q==}
1692
 
 
 
 
1693
  '@vitest/expect@1.6.1':
1694
  resolution: {integrity: sha512-jXL+9+ZNIJKruofqXuuTClf44eSpcHlgj3CiuNihUF3Ioujtmc0zIa3UJOW5RjDK1YLBJZnWBlPuqhYycLioog==}
1695
 
@@ -1756,6 +1798,9 @@ packages:
1756
  react-native-b4a:
1757
  optional: true
1758
 
 
 
 
1759
  bare-events@2.8.2:
1760
  resolution: {integrity: sha512-riJjyv1/mHLIPX4RwiK+oW9/4c3TEUeORHKefKAKnZ5kyslbN+HXowtbaVEqt4IMUB7OXlfixcs6gsFeo/jhiQ==}
1761
  peerDependencies:
@@ -1820,10 +1865,25 @@ packages:
1820
  caniuse-lite@1.0.30001735:
1821
  resolution: {integrity: sha512-EV/laoX7Wq2J9TQlyIXRxTJqIw4sxfXS4OYgudGxBYRuTv0q7AM6yMEpU/Vo1I94thg9U6EZ2NfZx9GJq83u7w==}
1822
 
 
 
 
1823
  chai@4.5.0:
1824
  resolution: {integrity: sha512-RITGBfijLkBddZvnn8jdqoTypxvqbOLYQkGGxXzeFjVHvudaPw0HNFD9x928/eUwYWd2dPCugVqspGALTZZQKw==}
1825
  engines: {node: '>=4'}
1826
 
 
 
 
 
 
 
 
 
 
 
 
 
1827
  check-error@1.0.3:
1828
  resolution: {integrity: sha512-iKEoDYaRmd1mxM90a2OEfWhjsjPpYPuQ+lMYsoxB126+t8fw7ySEO48nmDg5COTjxDI65/Y2OWpeEHk3ZOe8zg==}
1829
 
@@ -1870,6 +1930,13 @@ packages:
1870
  resolution: {integrity: sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==}
1871
  engines: {node: '>=12.5.0'}
1872
 
 
 
 
 
 
 
 
1873
  confbox@0.1.8:
1874
  resolution: {integrity: sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==}
1875
 
@@ -1955,6 +2022,9 @@ packages:
1955
  decimal.js-light@2.5.1:
1956
  resolution: {integrity: sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg==}
1957
 
 
 
 
1958
  deep-eql@4.1.4:
1959
  resolution: {integrity: sha512-SUwdGfqdKOwxCPeVYjwSyRpJ7Z+fhpwIAtmCUdZIWZ/YP5R9WAsyuSgpLVDi9bjWoN2LXHNss/dk3urXtdQxGg==}
1960
  engines: {node: '>=6'}
@@ -1963,6 +2033,10 @@ packages:
1963
  resolution: {integrity: sha512-TllpMR/t0M5sqCXfj85i4XaAzxmS5tVA16dqvdkMwGmzI+dXLXnw3J+3Vdv7VKw+ThlTMboK6i9rnZ6Nntj5CQ==}
1964
  engines: {node: '>= 14'}
1965
 
 
 
 
 
1966
  detect-libc@2.0.4:
1967
  resolution: {integrity: sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA==}
1968
  engines: {node: '>=8'}
@@ -1974,6 +2048,9 @@ packages:
1974
  detect-node-es@1.1.0:
1975
  resolution: {integrity: sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==}
1976
 
 
 
 
1977
  devtools-protocol@0.0.1595872:
1978
  resolution: {integrity: sha512-kRfgp8vWVjBu/fbYCiVFiOqsCk3CrMKEo3WbgGT2NXK2dG7vawWPBljixajVgGK9II8rDO9G0oD0zLt3I1daRg==}
1979
 
@@ -2007,6 +2084,10 @@ packages:
2007
  resolution: {integrity: sha512-d4lC8xfavMeBjzGr2vECC3fsGXziXZQyJxD868h2M/mBI3PwAuODxAkLkq5HYuvrPYcUtiLzsTo8U3PgX3Ocww==}
2008
  engines: {node: '>=10.13.0'}
2009
 
 
 
 
 
2010
  es-toolkit@1.39.9:
2011
  resolution: {integrity: sha512-9OtbkZmTA2Qc9groyA1PUNeb6knVTkvB2RSdr/LcJXDL8IdEakaxwXLHXa7VX/Wj0GmdMJPR3WhnPGhiP3E+qg==}
2012
 
@@ -2024,6 +2105,10 @@ packages:
2024
  resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==}
2025
  engines: {node: '>=6'}
2026
 
 
 
 
 
2027
  escodegen@2.1.0:
2028
  resolution: {integrity: sha512-2NlIDTwUWJN0mRPQOdtQBzbUHvdGY2P1VXSyU83Q3xKxM7WHX2Ql8dKq782Q9TgQUNOLEzEYu9bzLNj1q88I5w==}
2029
  engines: {node: '>=6.0'}
@@ -2038,6 +2123,9 @@ packages:
2038
  resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==}
2039
  engines: {node: '>=4.0'}
2040
 
 
 
 
2041
  estree-walker@3.0.3:
2042
  resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==}
2043
 
@@ -2055,6 +2143,9 @@ packages:
2055
  resolution: {integrity: sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg==}
2056
  engines: {node: '>=16.17'}
2057
 
 
 
 
2058
  extract-zip@2.0.1:
2059
  resolution: {integrity: sha512-GDhU9ntwuKyGXdZBUgTIe+vXnWj0fppUEtMDL0+idd5Sta8TGpHssn/eusA9mrPr9qNDym6SxAYZjNvCn/9RBg==}
2060
  engines: {node: '>= 10.17.0'}
@@ -2113,6 +2204,39 @@ packages:
2113
  graceful-fs@4.2.11:
2114
  resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==}
2115
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2116
  http-proxy-agent@7.0.2:
2117
  resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==}
2118
  engines: {node: '>= 14'}
@@ -2128,6 +2252,9 @@ packages:
2128
  immer@10.1.1:
2129
  resolution: {integrity: sha512-s2MPrmjovJcoMaHtx6K11Ra7oD05NT97w1IC5zpMkT6Atjr7H8LjaDd81iIxUYpMKSRRNMJE703M1Fhr/TctHw==}
2130
 
 
 
 
2131
  input-otp@1.4.1:
2132
  resolution: {integrity: sha512-+yvpmKYKHi9jIGngxagY9oWiiblPB7+nEO75F2l2o4vs+6vpPZZmUl4tBNYuTCvQjhvEIbdNeJu70bhfYP2nbw==}
2133
  peerDependencies:
@@ -2142,13 +2269,29 @@ packages:
2142
  resolution: {integrity: sha512-/+S6j4E9AHvW9SWMSEY9Xfy66O5PWvVEJ08O0y5JGyEKQpojb0K0GKpz/v5HJ/G0vi3D2sjGK78119oXZeE0qA==}
2143
  engines: {node: '>= 12'}
2144
 
 
 
 
 
 
 
2145
  is-arrayish@0.3.2:
2146
  resolution: {integrity: sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==}
2147
 
 
 
 
2148
  is-fullwidth-code-point@3.0.0:
2149
  resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==}
2150
  engines: {node: '>=8'}
2151
 
 
 
 
 
 
 
 
2152
  is-stream@3.0.0:
2153
  resolution: {integrity: sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA==}
2154
  engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0}
@@ -2163,6 +2306,14 @@ packages:
2163
  js-tokens@9.0.1:
2164
  resolution: {integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==}
2165
 
 
 
 
 
 
 
 
 
2166
  lightningcss-darwin-arm64@1.30.1:
2167
  resolution: {integrity: sha512-c8JK7hyE65X1MHMN+Viq9n11RRC7hgin3HhYKhrMyaXflk5GVplZ60IxyoVtzILeKr+xAJwg6zK6sjTBJ0FKYQ==}
2168
  engines: {node: '>= 12.0.0'}
@@ -2231,6 +2382,9 @@ packages:
2231
  resolution: {integrity: sha512-9rrA30MRRP3gBD3HTGnC6cDFpaE1kVDWxWgqWJUN0RvDNAo+Nz/9GxB+nHOH0ifbVFy0hSA1V6vFDvnx54lTEQ==}
2232
  engines: {node: '>=14'}
2233
 
 
 
 
2234
  loupe@2.3.7:
2235
  resolution: {integrity: sha512-zSMINGVYkdpYSOBmLi0D1Uo7JU9nVdQKrHxC8eYlV+9YKK9WePqAlL7lSlorG/U2Fw1w0hTBmaa/jrQ3UbPHtA==}
2236
 
@@ -2246,9 +2400,147 @@ packages:
2246
  magic-string@0.30.17:
2247
  resolution: {integrity: sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA==}
2248
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2249
  merge-stream@2.0.0:
2250
  resolution: {integrity: sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==}
2251
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2252
  mimic-fn@4.0.0:
2253
  resolution: {integrity: sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw==}
2254
  engines: {node: '>=12'}
@@ -2341,6 +2633,12 @@ packages:
2341
  resolution: {integrity: sha512-5NPgf87AT2STgwa2ntRMr45jTKrYBGkVU36yT0ig/n/GMAa3oPqhZfIQ2kMEimReg0+t9kZViDVZ83qfVUlckg==}
2342
  engines: {node: '>= 14'}
2343
 
 
 
 
 
 
 
2344
  path-key@3.1.1:
2345
  resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==}
2346
  engines: {node: '>=8'}
@@ -2396,6 +2694,9 @@ packages:
2396
  resolution: {integrity: sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==}
2397
  engines: {node: '>=0.4.0'}
2398
 
 
 
 
2399
  proxy-agent@6.5.0:
2400
  resolution: {integrity: sha512-TmatMXdr2KlRiA2CyDu8GqR8EjahTG3aY3nXjdzFyoZbmB8hrBsTyMezhULIXKnC0jpfjlmiZ3+EaCzoInSu/A==}
2401
  engines: {node: '>= 14'}
@@ -2433,6 +2734,12 @@ packages:
2433
  react-is@19.1.1:
2434
  resolution: {integrity: sha512-tr41fA15Vn8p4X9ntI+yCyeGSf1TlYaY5vlTZfQmeLBrFo3psOPX6HhTDnFNL9uj3EhP0KAQ80cugCl4b4BERA==}
2435
 
 
 
 
 
 
 
2436
  react-redux@9.2.0:
2437
  resolution: {integrity: sha512-ROY9fvHhwOD9ySfrF0wmvu//bKCQ6AeZZq1nJNtbDC+kk5DuSuNX/n6YWYF/SYy7bSba4D4FSz8DJeKY/S/r+g==}
2438
  peerDependencies:
@@ -2501,6 +2808,24 @@ packages:
2501
  redux@5.0.1:
2502
  resolution: {integrity: sha512-M9/ELqF6fy8FwmkpnF0S3YKOqMyoWJ4+CS5Efg2ct3oY9daQvd/Pc71FpGZsVsbl3Cpb+IIcjBDUnnyBdQbq4w==}
2503
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2504
  require-directory@2.1.1:
2505
  resolution: {integrity: sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==}
2506
  engines: {node: '>=0.10.0'}
@@ -2580,6 +2905,9 @@ packages:
2580
  resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==}
2581
  engines: {node: '>=0.10.0'}
2582
 
 
 
 
2583
  stackback@0.0.2:
2584
  resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==}
2585
 
@@ -2597,6 +2925,9 @@ packages:
2597
  resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==}
2598
  engines: {node: '>=8'}
2599
 
 
 
 
2600
  strip-ansi@6.0.1:
2601
  resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==}
2602
  engines: {node: '>=8'}
@@ -2608,6 +2939,12 @@ packages:
2608
  strip-literal@2.1.1:
2609
  resolution: {integrity: sha512-631UJ6O00eNGfMiWG78ck80dfBab8X6IVFB51jZK5Icd7XAs60Z5y7QdSd/wGIklnWvRbUNloVzhOKKmutxQ6Q==}
2610
 
 
 
 
 
 
 
2611
  styled-jsx@5.1.6:
2612
  resolution: {integrity: sha512-qSVyDTeMotdvQYoHWLNGwRFJHC+i+ZvdBRYosOFgC+Wg1vx4frN2/RG/NA7SYqqvKNLf39P2LSRA2pu6n0XYZA==}
2613
  engines: {node: '>= 12.0.0'}
@@ -2667,6 +3004,12 @@ packages:
2667
  resolution: {integrity: sha512-KYad6Vy5VDWV4GH3fjpseMQ/XU2BhIYP7Vzd0LG44qRWm/Yt2WCOTicFdvmgo6gWaqooMQCawTtILVQJupKu7A==}
2668
  engines: {node: '>=14.0.0'}
2669
 
 
 
 
 
 
 
2670
  tslib@2.8.1:
2671
  resolution: {integrity: sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==}
2672
 
@@ -2696,6 +3039,30 @@ packages:
2696
  undici-types@6.21.0:
2697
  resolution: {integrity: sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==}
2698
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2699
  update-browserslist-db@1.1.3:
2700
  resolution: {integrity: sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==}
2701
  hasBin: true
@@ -2733,6 +3100,15 @@ packages:
2733
  react: ^16.8 || ^17.0 || ^18.0
2734
  react-dom: ^16.8 || ^17.0 || ^18.0
2735
 
 
 
 
 
 
 
 
 
 
2736
  victory-vendor@37.3.6:
2737
  resolution: {integrity: sha512-SbPDPdDBYp+5MJHhBCAyI7wKM3d5ivekigc2Dk2s7pgbZ9wIgIBYGVw4zGHBml/qTFbexrofXW6Gu4noGxrOwQ==}
2738
 
@@ -2797,6 +3173,9 @@ packages:
2797
  jsdom:
2798
  optional: true
2799
 
 
 
 
2800
  webdriver-bidi-protocol@0.4.1:
2801
  resolution: {integrity: sha512-ARrjNjtWRRs2w4Tk7nqrf2gBI0QXWuOmMCx2hU+1jUt6d00MjMxURrhxhGbrsoiZKJrhTSTzbIrc554iKI10qw==}
2802
 
@@ -2855,6 +3234,9 @@ packages:
2855
  zod@3.25.67:
2856
  resolution: {integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==}
2857
 
 
 
 
2858
  snapshots:
2859
 
2860
  '@alloc/quick-lru@5.2.0': {}
@@ -4096,8 +4478,28 @@ snapshots:
4096
 
4097
  '@types/d3-timer@3.0.2': {}
4098
 
 
 
 
 
 
 
 
 
4099
  '@types/estree@1.0.8': {}
4100
 
 
 
 
 
 
 
 
 
 
 
 
 
4101
  '@types/node@22.17.2':
4102
  dependencies:
4103
  undici-types: 6.21.0
@@ -4110,6 +4512,10 @@ snapshots:
4110
  dependencies:
4111
  csstype: 3.1.3
4112
 
 
 
 
 
4113
  '@types/use-sync-external-store@0.0.6': {}
4114
 
4115
  '@types/yauzl@2.10.3':
@@ -4117,6 +4523,8 @@ snapshots:
4117
  '@types/node': 22.17.2
4118
  optional: true
4119
 
 
 
4120
  '@vitest/expect@1.6.1':
4121
  dependencies:
4122
  '@vitest/spy': 1.6.1
@@ -4184,6 +4592,8 @@ snapshots:
4184
 
4185
  b4a@1.8.1: {}
4186
 
 
 
4187
  bare-events@2.8.2: {}
4188
 
4189
  bare-fs@4.7.1:
@@ -4235,6 +4645,8 @@ snapshots:
4235
 
4236
  caniuse-lite@1.0.30001735: {}
4237
 
 
 
4238
  chai@4.5.0:
4239
  dependencies:
4240
  assertion-error: 1.1.0
@@ -4245,6 +4657,14 @@ snapshots:
4245
  pathval: 1.1.1
4246
  type-detect: 4.1.0
4247
 
 
 
 
 
 
 
 
 
4248
  check-error@1.0.3:
4249
  dependencies:
4250
  get-func-name: 2.0.2
@@ -4301,6 +4721,10 @@ snapshots:
4301
  color-string: 1.9.1
4302
  optional: true
4303
 
 
 
 
 
4304
  confbox@0.1.8: {}
4305
 
4306
  cross-spawn@7.0.6:
@@ -4365,6 +4789,10 @@ snapshots:
4365
 
4366
  decimal.js-light@2.5.1: {}
4367
 
 
 
 
 
4368
  deep-eql@4.1.4:
4369
  dependencies:
4370
  type-detect: 4.1.0
@@ -4375,12 +4803,18 @@ snapshots:
4375
  escodegen: 2.1.0
4376
  esprima: 4.0.1
4377
 
 
 
4378
  detect-libc@2.0.4: {}
4379
 
4380
  detect-libc@2.1.2: {}
4381
 
4382
  detect-node-es@1.1.0: {}
4383
 
 
 
 
 
4384
  devtools-protocol@0.0.1595872: {}
4385
 
4386
  diff-sequences@29.6.3: {}
@@ -4410,6 +4844,8 @@ snapshots:
4410
  graceful-fs: 4.2.11
4411
  tapable: 2.2.2
4412
 
 
 
4413
  es-toolkit@1.39.9: {}
4414
 
4415
  esbuild@0.21.5:
@@ -4469,6 +4905,8 @@ snapshots:
4469
 
4470
  escalade@3.2.0: {}
4471
 
 
 
4472
  escodegen@2.1.0:
4473
  dependencies:
4474
  esprima: 4.0.1
@@ -4481,6 +4919,8 @@ snapshots:
4481
 
4482
  estraverse@5.3.0: {}
4483
 
 
 
4484
  estree-walker@3.0.3:
4485
  dependencies:
4486
  '@types/estree': 1.0.8
@@ -4507,6 +4947,8 @@ snapshots:
4507
  signal-exit: 4.1.0
4508
  strip-final-newline: 3.0.0
4509
 
 
 
4510
  extract-zip@2.0.1:
4511
  dependencies:
4512
  debug: 4.4.3
@@ -4561,6 +5003,88 @@ snapshots:
4561
 
4562
  graceful-fs@4.2.11: {}
4563
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4564
  http-proxy-agent@7.0.2:
4565
  dependencies:
4566
  agent-base: 7.1.4
@@ -4579,6 +5103,8 @@ snapshots:
4579
 
4580
  immer@10.1.1: {}
4581
 
 
 
4582
  input-otp@1.4.1(react-dom@19.1.1(react@19.1.1))(react@19.1.1):
4583
  dependencies:
4584
  react: 19.1.1
@@ -4588,11 +5114,24 @@ snapshots:
4588
 
4589
  ip-address@10.2.0: {}
4590
 
 
 
 
 
 
 
 
4591
  is-arrayish@0.3.2:
4592
  optional: true
4593
 
 
 
4594
  is-fullwidth-code-point@3.0.0: {}
4595
 
 
 
 
 
4596
  is-stream@3.0.0: {}
4597
 
4598
  isexe@2.0.0: {}
@@ -4601,6 +5140,14 @@ snapshots:
4601
 
4602
  js-tokens@9.0.1: {}
4603
 
 
 
 
 
 
 
 
 
4604
  lightningcss-darwin-arm64@1.30.1:
4605
  optional: true
4606
 
@@ -4651,6 +5198,8 @@ snapshots:
4651
  mlly: 1.7.4
4652
  pkg-types: 1.3.1
4653
 
 
 
4654
  loupe@2.3.7:
4655
  dependencies:
4656
  get-func-name: 2.0.2
@@ -4665,8 +5214,376 @@ snapshots:
4665
  dependencies:
4666
  '@jridgewell/sourcemap-codec': 1.5.5
4667
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4668
  merge-stream@2.0.0: {}
4669
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4670
  mimic-fn@4.0.0: {}
4671
 
4672
  minipass@7.1.2: {}
@@ -4761,6 +5678,20 @@ snapshots:
4761
  degenerator: 5.0.1
4762
  netmask: 2.1.1
4763
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4764
  path-key@3.1.1: {}
4765
 
4766
  path-key@4.0.0: {}
@@ -4811,6 +5742,8 @@ snapshots:
4811
 
4812
  progress@2.0.3: {}
4813
 
 
 
4814
  proxy-agent@6.5.0:
4815
  dependencies:
4816
  agent-base: 7.1.4
@@ -4868,6 +5801,24 @@ snapshots:
4868
 
4869
  react-is@19.1.1: {}
4870
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4871
  react-redux@9.2.0(@types/react@19.1.10)(react@19.1.1)(redux@5.0.1):
4872
  dependencies:
4873
  '@types/use-sync-external-store': 0.0.6
@@ -4937,6 +5888,59 @@ snapshots:
4937
 
4938
  redux@5.0.1: {}
4939
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4940
  require-directory@2.1.1: {}
4941
 
4942
  reselect@5.1.1: {}
@@ -5045,6 +6049,8 @@ snapshots:
5045
  source-map@0.6.1:
5046
  optional: true
5047
 
 
 
5048
  stackback@0.0.2: {}
5049
 
5050
  std-env@3.9.0: {}
@@ -5066,6 +6072,11 @@ snapshots:
5066
  is-fullwidth-code-point: 3.0.0
5067
  strip-ansi: 6.0.1
5068
 
 
 
 
 
 
5069
  strip-ansi@6.0.1:
5070
  dependencies:
5071
  ansi-regex: 5.0.1
@@ -5076,6 +6087,14 @@ snapshots:
5076
  dependencies:
5077
  js-tokens: 9.0.1
5078
 
 
 
 
 
 
 
 
 
5079
  styled-jsx@5.1.6(react@19.1.1):
5080
  dependencies:
5081
  client-only: 0.0.1
@@ -5144,6 +6163,10 @@ snapshots:
5144
 
5145
  tinyspy@2.2.1: {}
5146
 
 
 
 
 
5147
  tslib@2.8.1: {}
5148
 
5149
  tsx@4.21.0:
@@ -5165,6 +6188,49 @@ snapshots:
5165
 
5166
  undici-types@6.21.0: {}
5167
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5168
  update-browserslist-db@1.1.3(browserslist@4.25.2):
5169
  dependencies:
5170
  browserslist: 4.25.2
@@ -5199,6 +6265,21 @@ snapshots:
5199
  - '@types/react'
5200
  - '@types/react-dom'
5201
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
5202
  victory-vendor@37.3.6:
5203
  dependencies:
5204
  '@types/d3-array': 3.2.1
@@ -5278,6 +6359,8 @@ snapshots:
5278
  - supports-color
5279
  - terser
5280
 
 
 
5281
  webdriver-bidi-protocol@0.4.1: {}
5282
 
5283
  which@2.0.2:
@@ -5323,3 +6406,5 @@ snapshots:
5323
  yocto-queue@1.2.1: {}
5324
 
5325
  zod@3.25.67: {}
 
 
 
119
  input-otp:
120
  specifier: 1.4.1
121
  version: 1.4.1(react-dom@19.1.1(react@19.1.1))(react@19.1.1)
122
+ katex:
123
+ specifier: ^0.17.0
124
+ version: 0.17.0
125
  lucide-react:
126
  specifier: ^0.454.0
127
  version: 0.454.0(react@19.1.1)
 
146
  react-is:
147
  specifier: ^19.1.1
148
  version: 19.1.1
149
+ react-markdown:
150
+ specifier: ^10.1.0
151
+ version: 10.1.0(@types/react@19.1.10)(react@19.1.1)
152
  react-resizable-panels:
153
  specifier: ^2.1.7
154
  version: 2.1.9(react-dom@19.1.1(react@19.1.1))(react@19.1.1)
155
  recharts:
156
  specifier: latest
157
  version: 3.8.1(@types/react@19.1.10)(react-dom@19.1.1(react@19.1.1))(react-is@19.1.1)(react@19.1.1)(redux@5.0.1)
158
+ rehype-katex:
159
+ specifier: ^7.0.1
160
+ version: 7.0.1
161
+ remark-gfm:
162
+ specifier: ^4.0.1
163
+ version: 4.0.1
164
+ remark-math:
165
+ specifier: ^6.0.0
166
+ version: 6.0.0
167
  server-only:
168
  specifier: ^0.0.1
169
  version: 0.0.1
 
1685
  '@types/d3-timer@3.0.2':
1686
  resolution: {integrity: sha512-Ps3T8E8dZDam6fUyNiMkekK3XUsaUEik+idO9/YjPtfj2qruF8tFBXS7XhtE4iIXBLxhmLjP3SXpLhVf21I9Lw==}
1687
 
1688
+ '@types/debug@4.1.13':
1689
+ resolution: {integrity: sha512-KSVgmQmzMwPlmtljOomayoR89W4FynCAi3E8PPs7vmDVPe84hT+vGPKkJfThkmXs0x0jAaa9U8uW8bbfyS2fWw==}
1690
+
1691
+ '@types/estree-jsx@1.0.5':
1692
+ resolution: {integrity: sha512-52CcUVNFyfb1A2ALocQw/Dd1BQFNmSdkuC3BkZ6iqhdMfQz7JWOFRuJFloOzjk+6WijU56m9oKXFAXc7o3Towg==}
1693
+
1694
  '@types/estree@1.0.8':
1695
  resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==}
1696
 
1697
+ '@types/hast@3.0.4':
1698
+ resolution: {integrity: sha512-WPs+bbQw5aCj+x6laNGWLH3wviHtoCv/P3+otBhbOhJgG8qtpdAMlTCxLtsTWA7LH1Oh/bFCHsBn0TPS5m30EQ==}
1699
+
1700
+ '@types/katex@0.16.8':
1701
+ resolution: {integrity: sha512-trgaNyfU+Xh2Tc+ABIb44a5AYUpicB3uwirOioeOkNPPbmgRNtcWyDeeFRzjPZENO9Vq8gvVqfhaaXWLlevVwg==}
1702
+
1703
+ '@types/mdast@4.0.4':
1704
+ resolution: {integrity: sha512-kGaNbPh1k7AFzgpud/gMdvIm5xuECykRR+JnWKQno9TAXVa6WIVCGTPvYGekIDL4uwCZQSYbUxNBSb1aUo79oA==}
1705
+
1706
+ '@types/ms@2.1.0':
1707
+ resolution: {integrity: sha512-GsCCIZDE/p3i96vtEqx+7dBUGXrc7zeSK3wwPHIaRThS+9OhWIXRqzs4d6k1SVU8g91DrNRWxWUGhp5KXQb2VA==}
1708
+
1709
  '@types/node@22.17.2':
1710
  resolution: {integrity: sha512-gL6z5N9Jm9mhY+U2KXZpteb+09zyffliRkZyZOHODGATyC5B1Jt/7TzuuiLkFsSUMLbS1OLmlj/E+/3KF4Q/4w==}
1711
 
 
1717
  '@types/react@19.1.10':
1718
  resolution: {integrity: sha512-EhBeSYX0Y6ye8pNebpKrwFJq7BoQ8J5SO6NlvNwwHjSj6adXJViPQrKlsyPw7hLBLvckEMO1yxeGdR82YBBlDg==}
1719
 
1720
+ '@types/unist@2.0.11':
1721
+ resolution: {integrity: sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==}
1722
+
1723
+ '@types/unist@3.0.3':
1724
+ resolution: {integrity: sha512-ko/gIFJRv177XgZsZcBwnqJN5x/Gien8qNOn0D5bQU/zAzVf9Zt3BlcUiLqhV9y4ARk0GbT3tnUiPNgnTXzc/Q==}
1725
+
1726
  '@types/use-sync-external-store@0.0.6':
1727
  resolution: {integrity: sha512-zFDAD+tlpf2r4asuHEj0XH6pY6i0g5NeAHPn+15wk3BV6JA69eERFXC1gyGThDkVa1zCyKr5jox1+2LbV/AMLg==}
1728
 
1729
  '@types/yauzl@2.10.3':
1730
  resolution: {integrity: sha512-oJoftv0LSuaDZE3Le4DbKX+KS9G36NzOeSap90UIK0yMA/NhKJhqlSGtNDORNRaIbQfzjXDrQa0ytJ6mNRGz/Q==}
1731
 
1732
+ '@ungap/structured-clone@1.3.1':
1733
+ resolution: {integrity: sha512-mUFwbeTqrVgDQxFveS+df2yfap6iuP20NAKAsBt5jDEoOTDew+zwLAOilHCeQJOVSvmgCX4ogqIrA0mnyr08yQ==}
1734
+
1735
  '@vitest/expect@1.6.1':
1736
  resolution: {integrity: sha512-jXL+9+ZNIJKruofqXuuTClf44eSpcHlgj3CiuNihUF3Ioujtmc0zIa3UJOW5RjDK1YLBJZnWBlPuqhYycLioog==}
1737
 
 
1798
  react-native-b4a:
1799
  optional: true
1800
 
1801
+ bail@2.0.2:
1802
+ resolution: {integrity: sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==}
1803
+
1804
  bare-events@2.8.2:
1805
  resolution: {integrity: sha512-riJjyv1/mHLIPX4RwiK+oW9/4c3TEUeORHKefKAKnZ5kyslbN+HXowtbaVEqt4IMUB7OXlfixcs6gsFeo/jhiQ==}
1806
  peerDependencies:
 
1865
  caniuse-lite@1.0.30001735:
1866
  resolution: {integrity: sha512-EV/laoX7Wq2J9TQlyIXRxTJqIw4sxfXS4OYgudGxBYRuTv0q7AM6yMEpU/Vo1I94thg9U6EZ2NfZx9GJq83u7w==}
1867
 
1868
+ ccount@2.0.1:
1869
+ resolution: {integrity: sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==}
1870
+
1871
  chai@4.5.0:
1872
  resolution: {integrity: sha512-RITGBfijLkBddZvnn8jdqoTypxvqbOLYQkGGxXzeFjVHvudaPw0HNFD9x928/eUwYWd2dPCugVqspGALTZZQKw==}
1873
  engines: {node: '>=4'}
1874
 
1875
+ character-entities-html4@2.1.0:
1876
+ resolution: {integrity: sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==}
1877
+
1878
+ character-entities-legacy@3.0.0:
1879
+ resolution: {integrity: sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==}
1880
+
1881
+ character-entities@2.0.2:
1882
+ resolution: {integrity: sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==}
1883
+
1884
+ character-reference-invalid@2.0.1:
1885
+ resolution: {integrity: sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==}
1886
+
1887
  check-error@1.0.3:
1888
  resolution: {integrity: sha512-iKEoDYaRmd1mxM90a2OEfWhjsjPpYPuQ+lMYsoxB126+t8fw7ySEO48nmDg5COTjxDI65/Y2OWpeEHk3ZOe8zg==}
1889
 
 
1930
  resolution: {integrity: sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A==}
1931
  engines: {node: '>=12.5.0'}
1932
 
1933
+ comma-separated-tokens@2.0.3:
1934
+ resolution: {integrity: sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==}
1935
+
1936
+ commander@8.3.0:
1937
+ resolution: {integrity: sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==}
1938
+ engines: {node: '>= 12'}
1939
+
1940
  confbox@0.1.8:
1941
  resolution: {integrity: sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==}
1942
 
 
2022
  decimal.js-light@2.5.1:
2023
  resolution: {integrity: sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg==}
2024
 
2025
+ decode-named-character-reference@1.3.0:
2026
+ resolution: {integrity: sha512-GtpQYB283KrPp6nRw50q3U9/VfOutZOe103qlN7BPP6Ad27xYnOIWv4lPzo8HCAL+mMZofJ9KEy30fq6MfaK6Q==}
2027
+
2028
  deep-eql@4.1.4:
2029
  resolution: {integrity: sha512-SUwdGfqdKOwxCPeVYjwSyRpJ7Z+fhpwIAtmCUdZIWZ/YP5R9WAsyuSgpLVDi9bjWoN2LXHNss/dk3urXtdQxGg==}
2030
  engines: {node: '>=6'}
 
2033
  resolution: {integrity: sha512-TllpMR/t0M5sqCXfj85i4XaAzxmS5tVA16dqvdkMwGmzI+dXLXnw3J+3Vdv7VKw+ThlTMboK6i9rnZ6Nntj5CQ==}
2034
  engines: {node: '>= 14'}
2035
 
2036
+ dequal@2.0.3:
2037
+ resolution: {integrity: sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==}
2038
+ engines: {node: '>=6'}
2039
+
2040
  detect-libc@2.0.4:
2041
  resolution: {integrity: sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA==}
2042
  engines: {node: '>=8'}
 
2048
  detect-node-es@1.1.0:
2049
  resolution: {integrity: sha512-ypdmJU/TbBby2Dxibuv7ZLW3Bs1QEmM7nHjEANfohJLvE0XVujisn1qPJcZxg+qDucsr+bP6fLD1rPS3AhJ7EQ==}
2050
 
2051
+ devlop@1.1.0:
2052
+ resolution: {integrity: sha512-RWmIqhcFf1lRYBvNmr7qTNuyCt/7/ns2jbpp1+PalgE/rDQcBT0fioSMUpJ93irlUhC5hrg4cYqe6U+0ImW0rA==}
2053
+
2054
  devtools-protocol@0.0.1595872:
2055
  resolution: {integrity: sha512-kRfgp8vWVjBu/fbYCiVFiOqsCk3CrMKEo3WbgGT2NXK2dG7vawWPBljixajVgGK9II8rDO9G0oD0zLt3I1daRg==}
2056
 
 
2084
  resolution: {integrity: sha512-d4lC8xfavMeBjzGr2vECC3fsGXziXZQyJxD868h2M/mBI3PwAuODxAkLkq5HYuvrPYcUtiLzsTo8U3PgX3Ocww==}
2085
  engines: {node: '>=10.13.0'}
2086
 
2087
+ entities@6.0.1:
2088
+ resolution: {integrity: sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==}
2089
+ engines: {node: '>=0.12'}
2090
+
2091
  es-toolkit@1.39.9:
2092
  resolution: {integrity: sha512-9OtbkZmTA2Qc9groyA1PUNeb6knVTkvB2RSdr/LcJXDL8IdEakaxwXLHXa7VX/Wj0GmdMJPR3WhnPGhiP3E+qg==}
2093
 
 
2105
  resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==}
2106
  engines: {node: '>=6'}
2107
 
2108
+ escape-string-regexp@5.0.0:
2109
+ resolution: {integrity: sha512-/veY75JbMK4j1yjvuUxuVsiS/hr/4iHs9FTT6cgTexxdE0Ly/glccBAkloH/DofkjRbZU3bnoj38mOmhkZ0lHw==}
2110
+ engines: {node: '>=12'}
2111
+
2112
  escodegen@2.1.0:
2113
  resolution: {integrity: sha512-2NlIDTwUWJN0mRPQOdtQBzbUHvdGY2P1VXSyU83Q3xKxM7WHX2Ql8dKq782Q9TgQUNOLEzEYu9bzLNj1q88I5w==}
2114
  engines: {node: '>=6.0'}
 
2123
  resolution: {integrity: sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==}
2124
  engines: {node: '>=4.0'}
2125
 
2126
+ estree-util-is-identifier-name@3.0.0:
2127
+ resolution: {integrity: sha512-hFtqIDZTIUZ9BXLb8y4pYGyk6+wekIivNVTcmvk8NoOh+VeRn5y6cEHzbURrWbfp1fIqdVipilzj+lfaadNZmg==}
2128
+
2129
  estree-walker@3.0.3:
2130
  resolution: {integrity: sha512-7RUKfXgSMMkzt6ZuXmqapOurLGPPfgj6l9uRZ7lRGolvk0y2yocc35LdcxKC5PQZdn2DMqioAQ2NoWcrTKmm6g==}
2131
 
 
2143
  resolution: {integrity: sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg==}
2144
  engines: {node: '>=16.17'}
2145
 
2146
+ extend@3.0.2:
2147
+ resolution: {integrity: sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==}
2148
+
2149
  extract-zip@2.0.1:
2150
  resolution: {integrity: sha512-GDhU9ntwuKyGXdZBUgTIe+vXnWj0fppUEtMDL0+idd5Sta8TGpHssn/eusA9mrPr9qNDym6SxAYZjNvCn/9RBg==}
2151
  engines: {node: '>= 10.17.0'}
 
2204
  graceful-fs@4.2.11:
2205
  resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==}
2206
 
2207
+ hast-util-from-dom@5.0.1:
2208
+ resolution: {integrity: sha512-N+LqofjR2zuzTjCPzyDUdSshy4Ma6li7p/c3pA78uTwzFgENbgbUrm2ugwsOdcjI1muO+o6Dgzp9p8WHtn/39Q==}
2209
+
2210
+ hast-util-from-html-isomorphic@2.0.0:
2211
+ resolution: {integrity: sha512-zJfpXq44yff2hmE0XmwEOzdWin5xwH+QIhMLOScpX91e/NSGPsAzNCvLQDIEPyO2TXi+lBmU6hjLIhV8MwP2kw==}
2212
+
2213
+ hast-util-from-html@2.0.3:
2214
+ resolution: {integrity: sha512-CUSRHXyKjzHov8yKsQjGOElXy/3EKpyX56ELnkHH34vDVw1N1XSQ1ZcAvTyAPtGqLTuKP/uxM+aLkSPqF/EtMw==}
2215
+
2216
+ hast-util-from-parse5@8.0.3:
2217
+ resolution: {integrity: sha512-3kxEVkEKt0zvcZ3hCRYI8rqrgwtlIOFMWkbclACvjlDw8Li9S2hk/d51OI0nr/gIpdMHNepwgOKqZ/sy0Clpyg==}
2218
+
2219
+ hast-util-is-element@3.0.0:
2220
+ resolution: {integrity: sha512-Val9mnv2IWpLbNPqc/pUem+a7Ipj2aHacCwgNfTiK0vJKl0LF+4Ba4+v1oPHFpf3bLYmreq0/l3Gud9S5OH42g==}
2221
+
2222
+ hast-util-parse-selector@4.0.0:
2223
+ resolution: {integrity: sha512-wkQCkSYoOGCRKERFWcxMVMOcYE2K1AaNLU8DXS9arxnLOUEWbOXKXiJUNzEpqZ3JOKpnha3jkFrumEjVliDe7A==}
2224
+
2225
+ hast-util-to-jsx-runtime@2.3.6:
2226
+ resolution: {integrity: sha512-zl6s8LwNyo1P9uw+XJGvZtdFF1GdAkOg8ujOw+4Pyb76874fLps4ueHXDhXWdk6YHQ6OgUtinliG7RsYvCbbBg==}
2227
+
2228
+ hast-util-to-text@4.0.2:
2229
+ resolution: {integrity: sha512-KK6y/BN8lbaq654j7JgBydev7wuNMcID54lkRav1P0CaE1e47P72AWWPiGKXTJU271ooYzcvTAn/Zt0REnvc7A==}
2230
+
2231
+ hast-util-whitespace@3.0.0:
2232
+ resolution: {integrity: sha512-88JUN06ipLwsnv+dVn+OIYOvAuvBMy/Qoi6O7mQHxdPXpjy+Cd6xRkWwux7DKO+4sYILtLBRIKgsdpS2gQc7qw==}
2233
+
2234
+ hastscript@9.0.1:
2235
+ resolution: {integrity: sha512-g7df9rMFX/SPi34tyGCyUBREQoKkapwdY/T04Qn9TDWfHhAYt4/I0gMVirzK5wEzeUqIjEB+LXC/ypb7Aqno5w==}
2236
+
2237
+ html-url-attributes@3.0.1:
2238
+ resolution: {integrity: sha512-ol6UPyBWqsrO6EJySPz2O7ZSr856WDrEzM5zMqp+FJJLGMW35cLYmmZnl0vztAZxRUoNZJFTCohfjuIJ8I4QBQ==}
2239
+
2240
  http-proxy-agent@7.0.2:
2241
  resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==}
2242
  engines: {node: '>= 14'}
 
2252
  immer@10.1.1:
2253
  resolution: {integrity: sha512-s2MPrmjovJcoMaHtx6K11Ra7oD05NT97w1IC5zpMkT6Atjr7H8LjaDd81iIxUYpMKSRRNMJE703M1Fhr/TctHw==}
2254
 
2255
+ inline-style-parser@0.2.7:
2256
+ resolution: {integrity: sha512-Nb2ctOyNR8DqQoR0OwRG95uNWIC0C1lCgf5Naz5H6Ji72KZ8OcFZLz2P5sNgwlyoJ8Yif11oMuYs5pBQa86csA==}
2257
+
2258
  input-otp@1.4.1:
2259
  resolution: {integrity: sha512-+yvpmKYKHi9jIGngxagY9oWiiblPB7+nEO75F2l2o4vs+6vpPZZmUl4tBNYuTCvQjhvEIbdNeJu70bhfYP2nbw==}
2260
  peerDependencies:
 
2269
  resolution: {integrity: sha512-/+S6j4E9AHvW9SWMSEY9Xfy66O5PWvVEJ08O0y5JGyEKQpojb0K0GKpz/v5HJ/G0vi3D2sjGK78119oXZeE0qA==}
2270
  engines: {node: '>= 12'}
2271
 
2272
+ is-alphabetical@2.0.1:
2273
+ resolution: {integrity: sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==}
2274
+
2275
+ is-alphanumerical@2.0.1:
2276
+ resolution: {integrity: sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==}
2277
+
2278
  is-arrayish@0.3.2:
2279
  resolution: {integrity: sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ==}
2280
 
2281
+ is-decimal@2.0.1:
2282
+ resolution: {integrity: sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==}
2283
+
2284
  is-fullwidth-code-point@3.0.0:
2285
  resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==}
2286
  engines: {node: '>=8'}
2287
 
2288
+ is-hexadecimal@2.0.1:
2289
+ resolution: {integrity: sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==}
2290
+
2291
+ is-plain-obj@4.1.0:
2292
+ resolution: {integrity: sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==}
2293
+ engines: {node: '>=12'}
2294
+
2295
  is-stream@3.0.0:
2296
  resolution: {integrity: sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA==}
2297
  engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0}
 
2306
  js-tokens@9.0.1:
2307
  resolution: {integrity: sha512-mxa9E9ITFOt0ban3j6L5MpjwegGz6lBQmM1IJkWeBZGcMxto50+eWdjC/52xDbS2vy0k7vIMK0Fe2wfL9OQSpQ==}
2308
 
2309
+ katex@0.16.47:
2310
+ resolution: {integrity: sha512-Eeo8Ys1doU1z+x8AZsPpQu+p/QcZBI5PeOo7QGQdy2x2m0MU/hYagBbGOmXwr5KVbEfVuWv9LpnQWeehogurjg==}
2311
+ hasBin: true
2312
+
2313
+ katex@0.17.0:
2314
+ resolution: {integrity: sha512-Vdw0ATsQ9V+LuegM/BTwQqV/6cTl5lbGcIrU+BCgLxyf6bo38ybOr372tuSIxir3CN720flu1meYR6XzNMwQnw==}
2315
+ hasBin: true
2316
+
2317
  lightningcss-darwin-arm64@1.30.1:
2318
  resolution: {integrity: sha512-c8JK7hyE65X1MHMN+Viq9n11RRC7hgin3HhYKhrMyaXflk5GVplZ60IxyoVtzILeKr+xAJwg6zK6sjTBJ0FKYQ==}
2319
  engines: {node: '>= 12.0.0'}
 
2382
  resolution: {integrity: sha512-9rrA30MRRP3gBD3HTGnC6cDFpaE1kVDWxWgqWJUN0RvDNAo+Nz/9GxB+nHOH0ifbVFy0hSA1V6vFDvnx54lTEQ==}
2383
  engines: {node: '>=14'}
2384
 
2385
+ longest-streak@3.1.0:
2386
+ resolution: {integrity: sha512-9Ri+o0JYgehTaVBBDoMqIl8GXtbWg711O3srftcHhZ0dqnETqLaoIK0x17fUw9rFSlK/0NlsKe0Ahhyl5pXE2g==}
2387
+
2388
  loupe@2.3.7:
2389
  resolution: {integrity: sha512-zSMINGVYkdpYSOBmLi0D1Uo7JU9nVdQKrHxC8eYlV+9YKK9WePqAlL7lSlorG/U2Fw1w0hTBmaa/jrQ3UbPHtA==}
2390
 
 
2400
  magic-string@0.30.17:
2401
  resolution: {integrity: sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA==}
2402
 
2403
+ markdown-table@3.0.4:
2404
+ resolution: {integrity: sha512-wiYz4+JrLyb/DqW2hkFJxP7Vd7JuTDm77fvbM8VfEQdmSMqcImWeeRbHwZjBjIFki/VaMK2BhFi7oUUZeM5bqw==}
2405
+
2406
+ mdast-util-find-and-replace@3.0.2:
2407
+ resolution: {integrity: sha512-Tmd1Vg/m3Xz43afeNxDIhWRtFZgM2VLyaf4vSTYwudTyeuTneoL3qtWMA5jeLyz/O1vDJmmV4QuScFCA2tBPwg==}
2408
+
2409
+ mdast-util-from-markdown@2.0.3:
2410
+ resolution: {integrity: sha512-W4mAWTvSlKvf8L6J+VN9yLSqQ9AOAAvHuoDAmPkz4dHf553m5gVj2ejadHJhoJmcmxEnOv6Pa8XJhpxE93kb8Q==}
2411
+
2412
+ mdast-util-gfm-autolink-literal@2.0.1:
2413
+ resolution: {integrity: sha512-5HVP2MKaP6L+G6YaxPNjuL0BPrq9orG3TsrZ9YXbA3vDw/ACI4MEsnoDpn6ZNm7GnZgtAcONJyPhOP8tNJQavQ==}
2414
+
2415
+ mdast-util-gfm-footnote@2.1.0:
2416
+ resolution: {integrity: sha512-sqpDWlsHn7Ac9GNZQMeUzPQSMzR6Wv0WKRNvQRg0KqHh02fpTz69Qc1QSseNX29bhz1ROIyNyxExfawVKTm1GQ==}
2417
+
2418
+ mdast-util-gfm-strikethrough@2.0.0:
2419
+ resolution: {integrity: sha512-mKKb915TF+OC5ptj5bJ7WFRPdYtuHv0yTRxK2tJvi+BDqbkiG7h7u/9SI89nRAYcmap2xHQL9D+QG/6wSrTtXg==}
2420
+
2421
+ mdast-util-gfm-table@2.0.0:
2422
+ resolution: {integrity: sha512-78UEvebzz/rJIxLvE7ZtDd/vIQ0RHv+3Mh5DR96p7cS7HsBhYIICDBCu8csTNWNO6tBWfqXPWekRuj2FNOGOZg==}
2423
+
2424
+ mdast-util-gfm-task-list-item@2.0.0:
2425
+ resolution: {integrity: sha512-IrtvNvjxC1o06taBAVJznEnkiHxLFTzgonUdy8hzFVeDun0uTjxxrRGVaNFqkU1wJR3RBPEfsxmU6jDWPofrTQ==}
2426
+
2427
+ mdast-util-gfm@3.1.0:
2428
+ resolution: {integrity: sha512-0ulfdQOM3ysHhCJ1p06l0b0VKlhU0wuQs3thxZQagjcjPrlFRqY215uZGHHJan9GEAXd9MbfPjFJz+qMkVR6zQ==}
2429
+
2430
+ mdast-util-math@3.0.0:
2431
+ resolution: {integrity: sha512-Tl9GBNeG/AhJnQM221bJR2HPvLOSnLE/T9cJI9tlc6zwQk2nPk/4f0cHkOdEixQPC/j8UtKDdITswvLAy1OZ1w==}
2432
+
2433
+ mdast-util-mdx-expression@2.0.1:
2434
+ resolution: {integrity: sha512-J6f+9hUp+ldTZqKRSg7Vw5V6MqjATc+3E4gf3CFNcuZNWD8XdyI6zQ8GqH7f8169MM6P7hMBRDVGnn7oHB9kXQ==}
2435
+
2436
+ mdast-util-mdx-jsx@3.2.0:
2437
+ resolution: {integrity: sha512-lj/z8v0r6ZtsN/cGNNtemmmfoLAFZnjMbNyLzBafjzikOM+glrjNHPlf6lQDOTccj9n5b0PPihEBbhneMyGs1Q==}
2438
+
2439
+ mdast-util-mdxjs-esm@2.0.1:
2440
+ resolution: {integrity: sha512-EcmOpxsZ96CvlP03NghtH1EsLtr0n9Tm4lPUJUBccV9RwUOneqSycg19n5HGzCf+10LozMRSObtVr3ee1WoHtg==}
2441
+
2442
+ mdast-util-phrasing@4.1.0:
2443
+ resolution: {integrity: sha512-TqICwyvJJpBwvGAMZjj4J2n0X8QWp21b9l0o7eXyVJ25YNWYbJDVIyD1bZXE6WtV6RmKJVYmQAKWa0zWOABz2w==}
2444
+
2445
+ mdast-util-to-hast@13.2.1:
2446
+ resolution: {integrity: sha512-cctsq2wp5vTsLIcaymblUriiTcZd0CwWtCbLvrOzYCDZoWyMNV8sZ7krj09FSnsiJi3WVsHLM4k6Dq/yaPyCXA==}
2447
+
2448
+ mdast-util-to-markdown@2.1.2:
2449
+ resolution: {integrity: sha512-xj68wMTvGXVOKonmog6LwyJKrYXZPvlwabaryTjLh9LuvovB/KAH+kvi8Gjj+7rJjsFi23nkUxRQv1KqSroMqA==}
2450
+
2451
+ mdast-util-to-string@4.0.0:
2452
+ resolution: {integrity: sha512-0H44vDimn51F0YwvxSJSm0eCDOJTRlmN0R1yBh4HLj9wiV1Dn0QoXGbvFAWj2hSItVTlCmBF1hqKlIyUBVFLPg==}
2453
+
2454
  merge-stream@2.0.0:
2455
  resolution: {integrity: sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==}
2456
 
2457
+ micromark-core-commonmark@2.0.3:
2458
+ resolution: {integrity: sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg==}
2459
+
2460
+ micromark-extension-gfm-autolink-literal@2.1.0:
2461
+ resolution: {integrity: sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw==}
2462
+
2463
+ micromark-extension-gfm-footnote@2.1.0:
2464
+ resolution: {integrity: sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw==}
2465
+
2466
+ micromark-extension-gfm-strikethrough@2.1.0:
2467
+ resolution: {integrity: sha512-ADVjpOOkjz1hhkZLlBiYA9cR2Anf8F4HqZUO6e5eDcPQd0Txw5fxLzzxnEkSkfnD0wziSGiv7sYhk/ktvbf1uw==}
2468
+
2469
+ micromark-extension-gfm-table@2.1.1:
2470
+ resolution: {integrity: sha512-t2OU/dXXioARrC6yWfJ4hqB7rct14e8f7m0cbI5hUmDyyIlwv5vEtooptH8INkbLzOatzKuVbQmAYcbWoyz6Dg==}
2471
+
2472
+ micromark-extension-gfm-tagfilter@2.0.0:
2473
+ resolution: {integrity: sha512-xHlTOmuCSotIA8TW1mDIM6X2O1SiX5P9IuDtqGonFhEK0qgRI4yeC6vMxEV2dgyr2TiD+2PQ10o+cOhdVAcwfg==}
2474
+
2475
+ micromark-extension-gfm-task-list-item@2.1.0:
2476
+ resolution: {integrity: sha512-qIBZhqxqI6fjLDYFTBIa4eivDMnP+OZqsNwmQ3xNLE4Cxwc+zfQEfbs6tzAo2Hjq+bh6q5F+Z8/cksrLFYWQQw==}
2477
+
2478
+ micromark-extension-gfm@3.0.0:
2479
+ resolution: {integrity: sha512-vsKArQsicm7t0z2GugkCKtZehqUm31oeGBV/KVSorWSy8ZlNAv7ytjFhvaryUiCUJYqs+NoE6AFhpQvBTM6Q4w==}
2480
+
2481
+ micromark-extension-math@3.1.0:
2482
+ resolution: {integrity: sha512-lvEqd+fHjATVs+2v/8kg9i5Q0AP2k85H0WUOwpIVvUML8BapsMvh1XAogmQjOCsLpoKRCVQqEkQBB3NhVBcsOg==}
2483
+
2484
+ micromark-factory-destination@2.0.1:
2485
+ resolution: {integrity: sha512-Xe6rDdJlkmbFRExpTOmRj9N3MaWmbAgdpSrBQvCFqhezUn4AHqJHbaEnfbVYYiexVSs//tqOdY/DxhjdCiJnIA==}
2486
+
2487
+ micromark-factory-label@2.0.1:
2488
+ resolution: {integrity: sha512-VFMekyQExqIW7xIChcXn4ok29YE3rnuyveW3wZQWWqF4Nv9Wk5rgJ99KzPvHjkmPXF93FXIbBp6YdW3t71/7Vg==}
2489
+
2490
+ micromark-factory-space@2.0.1:
2491
+ resolution: {integrity: sha512-zRkxjtBxxLd2Sc0d+fbnEunsTj46SWXgXciZmHq0kDYGnck/ZSGj9/wULTV95uoeYiK5hRXP2mJ98Uo4cq/LQg==}
2492
+
2493
+ micromark-factory-title@2.0.1:
2494
+ resolution: {integrity: sha512-5bZ+3CjhAd9eChYTHsjy6TGxpOFSKgKKJPJxr293jTbfry2KDoWkhBb6TcPVB4NmzaPhMs1Frm9AZH7OD4Cjzw==}
2495
+
2496
+ micromark-factory-whitespace@2.0.1:
2497
+ resolution: {integrity: sha512-Ob0nuZ3PKt/n0hORHyvoD9uZhr+Za8sFoP+OnMcnWK5lngSzALgQYKMr9RJVOWLqQYuyn6ulqGWSXdwf6F80lQ==}
2498
+
2499
+ micromark-util-character@2.1.1:
2500
+ resolution: {integrity: sha512-wv8tdUTJ3thSFFFJKtpYKOYiGP2+v96Hvk4Tu8KpCAsTMs6yi+nVmGh1syvSCsaxz45J6Jbw+9DD6g97+NV67Q==}
2501
+
2502
+ micromark-util-chunked@2.0.1:
2503
+ resolution: {integrity: sha512-QUNFEOPELfmvv+4xiNg2sRYeS/P84pTW0TCgP5zc9FpXetHY0ab7SxKyAQCNCc1eK0459uoLI1y5oO5Vc1dbhA==}
2504
+
2505
+ micromark-util-classify-character@2.0.1:
2506
+ resolution: {integrity: sha512-K0kHzM6afW/MbeWYWLjoHQv1sgg2Q9EccHEDzSkxiP/EaagNzCm7T/WMKZ3rjMbvIpvBiZgwR3dKMygtA4mG1Q==}
2507
+
2508
+ micromark-util-combine-extensions@2.0.1:
2509
+ resolution: {integrity: sha512-OnAnH8Ujmy59JcyZw8JSbK9cGpdVY44NKgSM7E9Eh7DiLS2E9RNQf0dONaGDzEG9yjEl5hcqeIsj4hfRkLH/Bg==}
2510
+
2511
+ micromark-util-decode-numeric-character-reference@2.0.2:
2512
+ resolution: {integrity: sha512-ccUbYk6CwVdkmCQMyr64dXz42EfHGkPQlBj5p7YVGzq8I7CtjXZJrubAYezf7Rp+bjPseiROqe7G6foFd+lEuw==}
2513
+
2514
+ micromark-util-decode-string@2.0.1:
2515
+ resolution: {integrity: sha512-nDV/77Fj6eH1ynwscYTOsbK7rR//Uj0bZXBwJZRfaLEJ1iGBR6kIfNmlNqaqJf649EP0F3NWNdeJi03elllNUQ==}
2516
+
2517
+ micromark-util-encode@2.0.1:
2518
+ resolution: {integrity: sha512-c3cVx2y4KqUnwopcO9b/SCdo2O67LwJJ/UyqGfbigahfegL9myoEFoDYZgkT7f36T0bLrM9hZTAaAyH+PCAXjw==}
2519
+
2520
+ micromark-util-html-tag-name@2.0.1:
2521
+ resolution: {integrity: sha512-2cNEiYDhCWKI+Gs9T0Tiysk136SnR13hhO8yW6BGNyhOC4qYFnwF1nKfD3HFAIXA5c45RrIG1ub11GiXeYd1xA==}
2522
+
2523
+ micromark-util-normalize-identifier@2.0.1:
2524
+ resolution: {integrity: sha512-sxPqmo70LyARJs0w2UclACPUUEqltCkJ6PhKdMIDuJ3gSf/Q+/GIe3WKl0Ijb/GyH9lOpUkRAO2wp0GVkLvS9Q==}
2525
+
2526
+ micromark-util-resolve-all@2.0.1:
2527
+ resolution: {integrity: sha512-VdQyxFWFT2/FGJgwQnJYbe1jjQoNTS4RjglmSjTUlpUMa95Htx9NHeYW4rGDJzbjvCsl9eLjMQwGeElsqmzcHg==}
2528
+
2529
+ micromark-util-sanitize-uri@2.0.1:
2530
+ resolution: {integrity: sha512-9N9IomZ/YuGGZZmQec1MbgxtlgougxTodVwDzzEouPKo3qFWvymFHWcnDi2vzV1ff6kas9ucW+o3yzJK9YB1AQ==}
2531
+
2532
+ micromark-util-subtokenize@2.1.0:
2533
+ resolution: {integrity: sha512-XQLu552iSctvnEcgXw6+Sx75GflAPNED1qx7eBJ+wydBb2KCbRZe+NwvIEEMM83uml1+2WSXpBAcp9IUCgCYWA==}
2534
+
2535
+ micromark-util-symbol@2.0.1:
2536
+ resolution: {integrity: sha512-vs5t8Apaud9N28kgCrRUdEed4UJ+wWNvicHLPxCa9ENlYuAY31M0ETy5y1vA33YoNPDFTghEbnh6efaE8h4x0Q==}
2537
+
2538
+ micromark-util-types@2.0.2:
2539
+ resolution: {integrity: sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA==}
2540
+
2541
+ micromark@4.0.2:
2542
+ resolution: {integrity: sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA==}
2543
+
2544
  mimic-fn@4.0.0:
2545
  resolution: {integrity: sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw==}
2546
  engines: {node: '>=12'}
 
2633
  resolution: {integrity: sha512-5NPgf87AT2STgwa2ntRMr45jTKrYBGkVU36yT0ig/n/GMAa3oPqhZfIQ2kMEimReg0+t9kZViDVZ83qfVUlckg==}
2634
  engines: {node: '>= 14'}
2635
 
2636
+ parse-entities@4.0.2:
2637
+ resolution: {integrity: sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw==}
2638
+
2639
+ parse5@7.3.0:
2640
+ resolution: {integrity: sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==}
2641
+
2642
  path-key@3.1.1:
2643
  resolution: {integrity: sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==}
2644
  engines: {node: '>=8'}
 
2694
  resolution: {integrity: sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==}
2695
  engines: {node: '>=0.4.0'}
2696
 
2697
+ property-information@7.2.0:
2698
+ resolution: {integrity: sha512-IAtzIB6sUiWaJYrX9smp3V46pBGbBeLFRGdh25kg1334VcBlD8HzhPeNIWQH9zhGmo2itIe25EHt9dQP7G5hmg==}
2699
+
2700
  proxy-agent@6.5.0:
2701
  resolution: {integrity: sha512-TmatMXdr2KlRiA2CyDu8GqR8EjahTG3aY3nXjdzFyoZbmB8hrBsTyMezhULIXKnC0jpfjlmiZ3+EaCzoInSu/A==}
2702
  engines: {node: '>= 14'}
 
2734
  react-is@19.1.1:
2735
  resolution: {integrity: sha512-tr41fA15Vn8p4X9ntI+yCyeGSf1TlYaY5vlTZfQmeLBrFo3psOPX6HhTDnFNL9uj3EhP0KAQ80cugCl4b4BERA==}
2736
 
2737
+ react-markdown@10.1.0:
2738
+ resolution: {integrity: sha512-qKxVopLT/TyA6BX3Ue5NwabOsAzm0Q7kAPwq6L+wWDwisYs7R8vZ0nRXqq6rkueboxpkjvLGU9fWifiX/ZZFxQ==}
2739
+ peerDependencies:
2740
+ '@types/react': '>=18'
2741
+ react: '>=18'
2742
+
2743
  react-redux@9.2.0:
2744
  resolution: {integrity: sha512-ROY9fvHhwOD9ySfrF0wmvu//bKCQ6AeZZq1nJNtbDC+kk5DuSuNX/n6YWYF/SYy7bSba4D4FSz8DJeKY/S/r+g==}
2745
  peerDependencies:
 
2808
  redux@5.0.1:
2809
  resolution: {integrity: sha512-M9/ELqF6fy8FwmkpnF0S3YKOqMyoWJ4+CS5Efg2ct3oY9daQvd/Pc71FpGZsVsbl3Cpb+IIcjBDUnnyBdQbq4w==}
2810
 
2811
+ rehype-katex@7.0.1:
2812
+ resolution: {integrity: sha512-OiM2wrZ/wuhKkigASodFoo8wimG3H12LWQaH8qSPVJn9apWKFSH3YOCtbKpBorTVw/eI7cuT21XBbvwEswbIOA==}
2813
+
2814
+ remark-gfm@4.0.1:
2815
+ resolution: {integrity: sha512-1quofZ2RQ9EWdeN34S79+KExV1764+wCUGop5CPL1WGdD0ocPpu91lzPGbwWMECpEpd42kJGQwzRfyov9j4yNg==}
2816
+
2817
+ remark-math@6.0.0:
2818
+ resolution: {integrity: sha512-MMqgnP74Igy+S3WwnhQ7kqGlEerTETXMvJhrUzDikVZ2/uogJCb+WHUg97hK9/jcfc0dkD73s3LN8zU49cTEtA==}
2819
+
2820
+ remark-parse@11.0.0:
2821
+ resolution: {integrity: sha512-FCxlKLNGknS5ba/1lmpYijMUzX2esxW5xQqjWxw2eHFfS2MSdaHVINFmhjo+qN1WhZhNimq0dZATN9pH0IDrpA==}
2822
+
2823
+ remark-rehype@11.1.2:
2824
+ resolution: {integrity: sha512-Dh7l57ianaEoIpzbp0PC9UKAdCSVklD8E5Rpw7ETfbTl3FqcOOgq5q2LVDhgGCkaBv7p24JXikPdvhhmHvKMsw==}
2825
+
2826
+ remark-stringify@11.0.0:
2827
+ resolution: {integrity: sha512-1OSmLd3awB/t8qdoEOMazZkNsfVTeY4fTsgzcQFdXNq8ToTN4ZGwrMnlda4K6smTFKD+GRV6O48i6Z4iKgPPpw==}
2828
+
2829
  require-directory@2.1.1:
2830
  resolution: {integrity: sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==}
2831
  engines: {node: '>=0.10.0'}
 
2905
  resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==}
2906
  engines: {node: '>=0.10.0'}
2907
 
2908
+ space-separated-tokens@2.0.2:
2909
+ resolution: {integrity: sha512-PEGlAwrG8yXGXRjW32fGbg66JAlOAwbObuqVoJpv/mRgoWDQfgH1wDPvtzWyUSNAXBGSk8h755YDbbcEy3SH2Q==}
2910
+
2911
  stackback@0.0.2:
2912
  resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==}
2913
 
 
2925
  resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==}
2926
  engines: {node: '>=8'}
2927
 
2928
+ stringify-entities@4.0.4:
2929
+ resolution: {integrity: sha512-IwfBptatlO+QCJUo19AqvrPNqlVMpW9YEL2LIVY+Rpv2qsjCGxaDLNRgeGsQWJhfItebuJhsGSLjaBbNSQ+ieg==}
2930
+
2931
  strip-ansi@6.0.1:
2932
  resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==}
2933
  engines: {node: '>=8'}
 
2939
  strip-literal@2.1.1:
2940
  resolution: {integrity: sha512-631UJ6O00eNGfMiWG78ck80dfBab8X6IVFB51jZK5Icd7XAs60Z5y7QdSd/wGIklnWvRbUNloVzhOKKmutxQ6Q==}
2941
 
2942
+ style-to-js@1.1.21:
2943
+ resolution: {integrity: sha512-RjQetxJrrUJLQPHbLku6U/ocGtzyjbJMP9lCNK7Ag0CNh690nSH8woqWH9u16nMjYBAok+i7JO1NP2pOy8IsPQ==}
2944
+
2945
+ style-to-object@1.0.14:
2946
+ resolution: {integrity: sha512-LIN7rULI0jBscWQYaSswptyderlarFkjQ+t79nzty8tcIAceVomEVlLzH5VP4Cmsv6MtKhs7qaAiwlcp+Mgaxw==}
2947
+
2948
  styled-jsx@5.1.6:
2949
  resolution: {integrity: sha512-qSVyDTeMotdvQYoHWLNGwRFJHC+i+ZvdBRYosOFgC+Wg1vx4frN2/RG/NA7SYqqvKNLf39P2LSRA2pu6n0XYZA==}
2950
  engines: {node: '>= 12.0.0'}
 
3004
  resolution: {integrity: sha512-KYad6Vy5VDWV4GH3fjpseMQ/XU2BhIYP7Vzd0LG44qRWm/Yt2WCOTicFdvmgo6gWaqooMQCawTtILVQJupKu7A==}
3005
  engines: {node: '>=14.0.0'}
3006
 
3007
+ trim-lines@3.0.1:
3008
+ resolution: {integrity: sha512-kRj8B+YHZCc9kQYdWfJB2/oUl9rA99qbowYYBtr4ui4mZyAQ2JpvVBd/6U2YloATfqBhBTSMhTpgBHtU0Mf3Rg==}
3009
+
3010
+ trough@2.2.0:
3011
+ resolution: {integrity: sha512-tmMpK00BjZiUyVyvrBK7knerNgmgvcV/KLVyuma/SC+TQN167GrMRciANTz09+k3zW8L8t60jWO1GpfkZdjTaw==}
3012
+
3013
  tslib@2.8.1:
3014
  resolution: {integrity: sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==}
3015
 
 
3039
  undici-types@6.21.0:
3040
  resolution: {integrity: sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==}
3041
 
3042
+ unified@11.0.5:
3043
+ resolution: {integrity: sha512-xKvGhPWw3k84Qjh8bI3ZeJjqnyadK+GEFtazSfZv/rKeTkTjOJho6mFqh2SM96iIcZokxiOpg78GazTSg8+KHA==}
3044
+
3045
+ unist-util-find-after@5.0.0:
3046
+ resolution: {integrity: sha512-amQa0Ep2m6hE2g72AugUItjbuM8X8cGQnFoHk0pGfrFeT9GZhzN5SW8nRsiGKK7Aif4CrACPENkA6P/Lw6fHGQ==}
3047
+
3048
+ unist-util-is@6.0.1:
3049
+ resolution: {integrity: sha512-LsiILbtBETkDz8I9p1dQ0uyRUWuaQzd/cuEeS1hoRSyW5E5XGmTzlwY1OrNzzakGowI9Dr/I8HVaw4hTtnxy8g==}
3050
+
3051
+ unist-util-position@5.0.0:
3052
+ resolution: {integrity: sha512-fucsC7HjXvkB5R3kTCO7kUjRdrS0BJt3M/FPxmHMBOm8JQi2BsHAHFsy27E0EolP8rp0NzXsJ+jNPyDWvOJZPA==}
3053
+
3054
+ unist-util-remove-position@5.0.0:
3055
+ resolution: {integrity: sha512-Hp5Kh3wLxv0PHj9m2yZhhLt58KzPtEYKQQ4yxfYFEO7EvHwzyDYnduhHnY1mDxoqr7VUwVuHXk9RXKIiYS1N8Q==}
3056
+
3057
+ unist-util-stringify-position@4.0.0:
3058
+ resolution: {integrity: sha512-0ASV06AAoKCDkS2+xw5RXJywruurpbC4JZSm7nr7MOt1ojAzvyyaO+UxZf18j8FCF6kmzCZKcAgN/yu2gm2XgQ==}
3059
+
3060
+ unist-util-visit-parents@6.0.2:
3061
+ resolution: {integrity: sha512-goh1s1TBrqSqukSc8wrjwWhL0hiJxgA8m4kFxGlQ+8FYQ3C/m11FcTs4YYem7V664AhHVvgoQLk890Ssdsr2IQ==}
3062
+
3063
+ unist-util-visit@5.1.0:
3064
+ resolution: {integrity: sha512-m+vIdyeCOpdr/QeQCu2EzxX/ohgS8KbnPDgFni4dQsfSCtpz8UqDyY5GjRru8PDKuYn7Fq19j1CQ+nJSsGKOzg==}
3065
+
3066
  update-browserslist-db@1.1.3:
3067
  resolution: {integrity: sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==}
3068
  hasBin: true
 
3100
  react: ^16.8 || ^17.0 || ^18.0
3101
  react-dom: ^16.8 || ^17.0 || ^18.0
3102
 
3103
+ vfile-location@5.0.3:
3104
+ resolution: {integrity: sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg==}
3105
+
3106
+ vfile-message@4.0.3:
3107
+ resolution: {integrity: sha512-QTHzsGd1EhbZs4AsQ20JX1rC3cOlt/IWJruk893DfLRr57lcnOeMaWG4K0JrRta4mIJZKth2Au3mM3u03/JWKw==}
3108
+
3109
+ vfile@6.0.3:
3110
+ resolution: {integrity: sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q==}
3111
+
3112
  victory-vendor@37.3.6:
3113
  resolution: {integrity: sha512-SbPDPdDBYp+5MJHhBCAyI7wKM3d5ivekigc2Dk2s7pgbZ9wIgIBYGVw4zGHBml/qTFbexrofXW6Gu4noGxrOwQ==}
3114
 
 
3173
  jsdom:
3174
  optional: true
3175
 
3176
+ web-namespaces@2.0.1:
3177
+ resolution: {integrity: sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ==}
3178
+
3179
  webdriver-bidi-protocol@0.4.1:
3180
  resolution: {integrity: sha512-ARrjNjtWRRs2w4Tk7nqrf2gBI0QXWuOmMCx2hU+1jUt6d00MjMxURrhxhGbrsoiZKJrhTSTzbIrc554iKI10qw==}
3181
 
 
3234
  zod@3.25.67:
3235
  resolution: {integrity: sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==}
3236
 
3237
+ zwitch@2.0.4:
3238
+ resolution: {integrity: sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==}
3239
+
3240
  snapshots:
3241
 
3242
  '@alloc/quick-lru@5.2.0': {}
 
4478
 
4479
  '@types/d3-timer@3.0.2': {}
4480
 
4481
+ '@types/debug@4.1.13':
4482
+ dependencies:
4483
+ '@types/ms': 2.1.0
4484
+
4485
+ '@types/estree-jsx@1.0.5':
4486
+ dependencies:
4487
+ '@types/estree': 1.0.8
4488
+
4489
  '@types/estree@1.0.8': {}
4490
 
4491
+ '@types/hast@3.0.4':
4492
+ dependencies:
4493
+ '@types/unist': 3.0.3
4494
+
4495
+ '@types/katex@0.16.8': {}
4496
+
4497
+ '@types/mdast@4.0.4':
4498
+ dependencies:
4499
+ '@types/unist': 3.0.3
4500
+
4501
+ '@types/ms@2.1.0': {}
4502
+
4503
  '@types/node@22.17.2':
4504
  dependencies:
4505
  undici-types: 6.21.0
 
4512
  dependencies:
4513
  csstype: 3.1.3
4514
 
4515
+ '@types/unist@2.0.11': {}
4516
+
4517
+ '@types/unist@3.0.3': {}
4518
+
4519
  '@types/use-sync-external-store@0.0.6': {}
4520
 
4521
  '@types/yauzl@2.10.3':
 
4523
  '@types/node': 22.17.2
4524
  optional: true
4525
 
4526
+ '@ungap/structured-clone@1.3.1': {}
4527
+
4528
  '@vitest/expect@1.6.1':
4529
  dependencies:
4530
  '@vitest/spy': 1.6.1
 
4592
 
4593
  b4a@1.8.1: {}
4594
 
4595
+ bail@2.0.2: {}
4596
+
4597
  bare-events@2.8.2: {}
4598
 
4599
  bare-fs@4.7.1:
 
4645
 
4646
  caniuse-lite@1.0.30001735: {}
4647
 
4648
+ ccount@2.0.1: {}
4649
+
4650
  chai@4.5.0:
4651
  dependencies:
4652
  assertion-error: 1.1.0
 
4657
  pathval: 1.1.1
4658
  type-detect: 4.1.0
4659
 
4660
+ character-entities-html4@2.1.0: {}
4661
+
4662
+ character-entities-legacy@3.0.0: {}
4663
+
4664
+ character-entities@2.0.2: {}
4665
+
4666
+ character-reference-invalid@2.0.1: {}
4667
+
4668
  check-error@1.0.3:
4669
  dependencies:
4670
  get-func-name: 2.0.2
 
4721
  color-string: 1.9.1
4722
  optional: true
4723
 
4724
+ comma-separated-tokens@2.0.3: {}
4725
+
4726
+ commander@8.3.0: {}
4727
+
4728
  confbox@0.1.8: {}
4729
 
4730
  cross-spawn@7.0.6:
 
4789
 
4790
  decimal.js-light@2.5.1: {}
4791
 
4792
+ decode-named-character-reference@1.3.0:
4793
+ dependencies:
4794
+ character-entities: 2.0.2
4795
+
4796
  deep-eql@4.1.4:
4797
  dependencies:
4798
  type-detect: 4.1.0
 
4803
  escodegen: 2.1.0
4804
  esprima: 4.0.1
4805
 
4806
+ dequal@2.0.3: {}
4807
+
4808
  detect-libc@2.0.4: {}
4809
 
4810
  detect-libc@2.1.2: {}
4811
 
4812
  detect-node-es@1.1.0: {}
4813
 
4814
+ devlop@1.1.0:
4815
+ dependencies:
4816
+ dequal: 2.0.3
4817
+
4818
  devtools-protocol@0.0.1595872: {}
4819
 
4820
  diff-sequences@29.6.3: {}
 
4844
  graceful-fs: 4.2.11
4845
  tapable: 2.2.2
4846
 
4847
+ entities@6.0.1: {}
4848
+
4849
  es-toolkit@1.39.9: {}
4850
 
4851
  esbuild@0.21.5:
 
4905
 
4906
  escalade@3.2.0: {}
4907
 
4908
+ escape-string-regexp@5.0.0: {}
4909
+
4910
  escodegen@2.1.0:
4911
  dependencies:
4912
  esprima: 4.0.1
 
4919
 
4920
  estraverse@5.3.0: {}
4921
 
4922
+ estree-util-is-identifier-name@3.0.0: {}
4923
+
4924
  estree-walker@3.0.3:
4925
  dependencies:
4926
  '@types/estree': 1.0.8
 
4947
  signal-exit: 4.1.0
4948
  strip-final-newline: 3.0.0
4949
 
4950
+ extend@3.0.2: {}
4951
+
4952
  extract-zip@2.0.1:
4953
  dependencies:
4954
  debug: 4.4.3
 
5003
 
5004
  graceful-fs@4.2.11: {}
5005
 
5006
+ hast-util-from-dom@5.0.1:
5007
+ dependencies:
5008
+ '@types/hast': 3.0.4
5009
+ hastscript: 9.0.1
5010
+ web-namespaces: 2.0.1
5011
+
5012
+ hast-util-from-html-isomorphic@2.0.0:
5013
+ dependencies:
5014
+ '@types/hast': 3.0.4
5015
+ hast-util-from-dom: 5.0.1
5016
+ hast-util-from-html: 2.0.3
5017
+ unist-util-remove-position: 5.0.0
5018
+
5019
+ hast-util-from-html@2.0.3:
5020
+ dependencies:
5021
+ '@types/hast': 3.0.4
5022
+ devlop: 1.1.0
5023
+ hast-util-from-parse5: 8.0.3
5024
+ parse5: 7.3.0
5025
+ vfile: 6.0.3
5026
+ vfile-message: 4.0.3
5027
+
5028
+ hast-util-from-parse5@8.0.3:
5029
+ dependencies:
5030
+ '@types/hast': 3.0.4
5031
+ '@types/unist': 3.0.3
5032
+ devlop: 1.1.0
5033
+ hastscript: 9.0.1
5034
+ property-information: 7.2.0
5035
+ vfile: 6.0.3
5036
+ vfile-location: 5.0.3
5037
+ web-namespaces: 2.0.1
5038
+
5039
+ hast-util-is-element@3.0.0:
5040
+ dependencies:
5041
+ '@types/hast': 3.0.4
5042
+
5043
+ hast-util-parse-selector@4.0.0:
5044
+ dependencies:
5045
+ '@types/hast': 3.0.4
5046
+
5047
+ hast-util-to-jsx-runtime@2.3.6:
5048
+ dependencies:
5049
+ '@types/estree': 1.0.8
5050
+ '@types/hast': 3.0.4
5051
+ '@types/unist': 3.0.3
5052
+ comma-separated-tokens: 2.0.3
5053
+ devlop: 1.1.0
5054
+ estree-util-is-identifier-name: 3.0.0
5055
+ hast-util-whitespace: 3.0.0
5056
+ mdast-util-mdx-expression: 2.0.1
5057
+ mdast-util-mdx-jsx: 3.2.0
5058
+ mdast-util-mdxjs-esm: 2.0.1
5059
+ property-information: 7.2.0
5060
+ space-separated-tokens: 2.0.2
5061
+ style-to-js: 1.1.21
5062
+ unist-util-position: 5.0.0
5063
+ vfile-message: 4.0.3
5064
+ transitivePeerDependencies:
5065
+ - supports-color
5066
+
5067
+ hast-util-to-text@4.0.2:
5068
+ dependencies:
5069
+ '@types/hast': 3.0.4
5070
+ '@types/unist': 3.0.3
5071
+ hast-util-is-element: 3.0.0
5072
+ unist-util-find-after: 5.0.0
5073
+
5074
+ hast-util-whitespace@3.0.0:
5075
+ dependencies:
5076
+ '@types/hast': 3.0.4
5077
+
5078
+ hastscript@9.0.1:
5079
+ dependencies:
5080
+ '@types/hast': 3.0.4
5081
+ comma-separated-tokens: 2.0.3
5082
+ hast-util-parse-selector: 4.0.0
5083
+ property-information: 7.2.0
5084
+ space-separated-tokens: 2.0.2
5085
+
5086
+ html-url-attributes@3.0.1: {}
5087
+
5088
  http-proxy-agent@7.0.2:
5089
  dependencies:
5090
  agent-base: 7.1.4
 
5103
 
5104
  immer@10.1.1: {}
5105
 
5106
+ inline-style-parser@0.2.7: {}
5107
+
5108
  input-otp@1.4.1(react-dom@19.1.1(react@19.1.1))(react@19.1.1):
5109
  dependencies:
5110
  react: 19.1.1
 
5114
 
5115
  ip-address@10.2.0: {}
5116
 
5117
+ is-alphabetical@2.0.1: {}
5118
+
5119
+ is-alphanumerical@2.0.1:
5120
+ dependencies:
5121
+ is-alphabetical: 2.0.1
5122
+ is-decimal: 2.0.1
5123
+
5124
  is-arrayish@0.3.2:
5125
  optional: true
5126
 
5127
+ is-decimal@2.0.1: {}
5128
+
5129
  is-fullwidth-code-point@3.0.0: {}
5130
 
5131
+ is-hexadecimal@2.0.1: {}
5132
+
5133
+ is-plain-obj@4.1.0: {}
5134
+
5135
  is-stream@3.0.0: {}
5136
 
5137
  isexe@2.0.0: {}
 
5140
 
5141
  js-tokens@9.0.1: {}
5142
 
5143
+ katex@0.16.47:
5144
+ dependencies:
5145
+ commander: 8.3.0
5146
+
5147
+ katex@0.17.0:
5148
+ dependencies:
5149
+ commander: 8.3.0
5150
+
5151
  lightningcss-darwin-arm64@1.30.1:
5152
  optional: true
5153
 
 
5198
  mlly: 1.7.4
5199
  pkg-types: 1.3.1
5200
 
5201
+ longest-streak@3.1.0: {}
5202
+
5203
  loupe@2.3.7:
5204
  dependencies:
5205
  get-func-name: 2.0.2
 
5214
  dependencies:
5215
  '@jridgewell/sourcemap-codec': 1.5.5
5216
 
5217
+ markdown-table@3.0.4: {}
5218
+
5219
+ mdast-util-find-and-replace@3.0.2:
5220
+ dependencies:
5221
+ '@types/mdast': 4.0.4
5222
+ escape-string-regexp: 5.0.0
5223
+ unist-util-is: 6.0.1
5224
+ unist-util-visit-parents: 6.0.2
5225
+
5226
+ mdast-util-from-markdown@2.0.3:
5227
+ dependencies:
5228
+ '@types/mdast': 4.0.4
5229
+ '@types/unist': 3.0.3
5230
+ decode-named-character-reference: 1.3.0
5231
+ devlop: 1.1.0
5232
+ mdast-util-to-string: 4.0.0
5233
+ micromark: 4.0.2
5234
+ micromark-util-decode-numeric-character-reference: 2.0.2
5235
+ micromark-util-decode-string: 2.0.1
5236
+ micromark-util-normalize-identifier: 2.0.1
5237
+ micromark-util-symbol: 2.0.1
5238
+ micromark-util-types: 2.0.2
5239
+ unist-util-stringify-position: 4.0.0
5240
+ transitivePeerDependencies:
5241
+ - supports-color
5242
+
5243
+ mdast-util-gfm-autolink-literal@2.0.1:
5244
+ dependencies:
5245
+ '@types/mdast': 4.0.4
5246
+ ccount: 2.0.1
5247
+ devlop: 1.1.0
5248
+ mdast-util-find-and-replace: 3.0.2
5249
+ micromark-util-character: 2.1.1
5250
+
5251
+ mdast-util-gfm-footnote@2.1.0:
5252
+ dependencies:
5253
+ '@types/mdast': 4.0.4
5254
+ devlop: 1.1.0
5255
+ mdast-util-from-markdown: 2.0.3
5256
+ mdast-util-to-markdown: 2.1.2
5257
+ micromark-util-normalize-identifier: 2.0.1
5258
+ transitivePeerDependencies:
5259
+ - supports-color
5260
+
5261
+ mdast-util-gfm-strikethrough@2.0.0:
5262
+ dependencies:
5263
+ '@types/mdast': 4.0.4
5264
+ mdast-util-from-markdown: 2.0.3
5265
+ mdast-util-to-markdown: 2.1.2
5266
+ transitivePeerDependencies:
5267
+ - supports-color
5268
+
5269
+ mdast-util-gfm-table@2.0.0:
5270
+ dependencies:
5271
+ '@types/mdast': 4.0.4
5272
+ devlop: 1.1.0
5273
+ markdown-table: 3.0.4
5274
+ mdast-util-from-markdown: 2.0.3
5275
+ mdast-util-to-markdown: 2.1.2
5276
+ transitivePeerDependencies:
5277
+ - supports-color
5278
+
5279
+ mdast-util-gfm-task-list-item@2.0.0:
5280
+ dependencies:
5281
+ '@types/mdast': 4.0.4
5282
+ devlop: 1.1.0
5283
+ mdast-util-from-markdown: 2.0.3
5284
+ mdast-util-to-markdown: 2.1.2
5285
+ transitivePeerDependencies:
5286
+ - supports-color
5287
+
5288
+ mdast-util-gfm@3.1.0:
5289
+ dependencies:
5290
+ mdast-util-from-markdown: 2.0.3
5291
+ mdast-util-gfm-autolink-literal: 2.0.1
5292
+ mdast-util-gfm-footnote: 2.1.0
5293
+ mdast-util-gfm-strikethrough: 2.0.0
5294
+ mdast-util-gfm-table: 2.0.0
5295
+ mdast-util-gfm-task-list-item: 2.0.0
5296
+ mdast-util-to-markdown: 2.1.2
5297
+ transitivePeerDependencies:
5298
+ - supports-color
5299
+
5300
+ mdast-util-math@3.0.0:
5301
+ dependencies:
5302
+ '@types/hast': 3.0.4
5303
+ '@types/mdast': 4.0.4
5304
+ devlop: 1.1.0
5305
+ longest-streak: 3.1.0
5306
+ mdast-util-from-markdown: 2.0.3
5307
+ mdast-util-to-markdown: 2.1.2
5308
+ unist-util-remove-position: 5.0.0
5309
+ transitivePeerDependencies:
5310
+ - supports-color
5311
+
5312
+ mdast-util-mdx-expression@2.0.1:
5313
+ dependencies:
5314
+ '@types/estree-jsx': 1.0.5
5315
+ '@types/hast': 3.0.4
5316
+ '@types/mdast': 4.0.4
5317
+ devlop: 1.1.0
5318
+ mdast-util-from-markdown: 2.0.3
5319
+ mdast-util-to-markdown: 2.1.2
5320
+ transitivePeerDependencies:
5321
+ - supports-color
5322
+
5323
+ mdast-util-mdx-jsx@3.2.0:
5324
+ dependencies:
5325
+ '@types/estree-jsx': 1.0.5
5326
+ '@types/hast': 3.0.4
5327
+ '@types/mdast': 4.0.4
5328
+ '@types/unist': 3.0.3
5329
+ ccount: 2.0.1
5330
+ devlop: 1.1.0
5331
+ mdast-util-from-markdown: 2.0.3
5332
+ mdast-util-to-markdown: 2.1.2
5333
+ parse-entities: 4.0.2
5334
+ stringify-entities: 4.0.4
5335
+ unist-util-stringify-position: 4.0.0
5336
+ vfile-message: 4.0.3
5337
+ transitivePeerDependencies:
5338
+ - supports-color
5339
+
5340
+ mdast-util-mdxjs-esm@2.0.1:
5341
+ dependencies:
5342
+ '@types/estree-jsx': 1.0.5
5343
+ '@types/hast': 3.0.4
5344
+ '@types/mdast': 4.0.4
5345
+ devlop: 1.1.0
5346
+ mdast-util-from-markdown: 2.0.3
5347
+ mdast-util-to-markdown: 2.1.2
5348
+ transitivePeerDependencies:
5349
+ - supports-color
5350
+
5351
+ mdast-util-phrasing@4.1.0:
5352
+ dependencies:
5353
+ '@types/mdast': 4.0.4
5354
+ unist-util-is: 6.0.1
5355
+
5356
+ mdast-util-to-hast@13.2.1:
5357
+ dependencies:
5358
+ '@types/hast': 3.0.4
5359
+ '@types/mdast': 4.0.4
5360
+ '@ungap/structured-clone': 1.3.1
5361
+ devlop: 1.1.0
5362
+ micromark-util-sanitize-uri: 2.0.1
5363
+ trim-lines: 3.0.1
5364
+ unist-util-position: 5.0.0
5365
+ unist-util-visit: 5.1.0
5366
+ vfile: 6.0.3
5367
+
5368
+ mdast-util-to-markdown@2.1.2:
5369
+ dependencies:
5370
+ '@types/mdast': 4.0.4
5371
+ '@types/unist': 3.0.3
5372
+ longest-streak: 3.1.0
5373
+ mdast-util-phrasing: 4.1.0
5374
+ mdast-util-to-string: 4.0.0
5375
+ micromark-util-classify-character: 2.0.1
5376
+ micromark-util-decode-string: 2.0.1
5377
+ unist-util-visit: 5.1.0
5378
+ zwitch: 2.0.4
5379
+
5380
+ mdast-util-to-string@4.0.0:
5381
+ dependencies:
5382
+ '@types/mdast': 4.0.4
5383
+
5384
  merge-stream@2.0.0: {}
5385
 
5386
+ micromark-core-commonmark@2.0.3:
5387
+ dependencies:
5388
+ decode-named-character-reference: 1.3.0
5389
+ devlop: 1.1.0
5390
+ micromark-factory-destination: 2.0.1
5391
+ micromark-factory-label: 2.0.1
5392
+ micromark-factory-space: 2.0.1
5393
+ micromark-factory-title: 2.0.1
5394
+ micromark-factory-whitespace: 2.0.1
5395
+ micromark-util-character: 2.1.1
5396
+ micromark-util-chunked: 2.0.1
5397
+ micromark-util-classify-character: 2.0.1
5398
+ micromark-util-html-tag-name: 2.0.1
5399
+ micromark-util-normalize-identifier: 2.0.1
5400
+ micromark-util-resolve-all: 2.0.1
5401
+ micromark-util-subtokenize: 2.1.0
5402
+ micromark-util-symbol: 2.0.1
5403
+ micromark-util-types: 2.0.2
5404
+
5405
+ micromark-extension-gfm-autolink-literal@2.1.0:
5406
+ dependencies:
5407
+ micromark-util-character: 2.1.1
5408
+ micromark-util-sanitize-uri: 2.0.1
5409
+ micromark-util-symbol: 2.0.1
5410
+ micromark-util-types: 2.0.2
5411
+
5412
+ micromark-extension-gfm-footnote@2.1.0:
5413
+ dependencies:
5414
+ devlop: 1.1.0
5415
+ micromark-core-commonmark: 2.0.3
5416
+ micromark-factory-space: 2.0.1
5417
+ micromark-util-character: 2.1.1
5418
+ micromark-util-normalize-identifier: 2.0.1
5419
+ micromark-util-sanitize-uri: 2.0.1
5420
+ micromark-util-symbol: 2.0.1
5421
+ micromark-util-types: 2.0.2
5422
+
5423
+ micromark-extension-gfm-strikethrough@2.1.0:
5424
+ dependencies:
5425
+ devlop: 1.1.0
5426
+ micromark-util-chunked: 2.0.1
5427
+ micromark-util-classify-character: 2.0.1
5428
+ micromark-util-resolve-all: 2.0.1
5429
+ micromark-util-symbol: 2.0.1
5430
+ micromark-util-types: 2.0.2
5431
+
5432
+ micromark-extension-gfm-table@2.1.1:
5433
+ dependencies:
5434
+ devlop: 1.1.0
5435
+ micromark-factory-space: 2.0.1
5436
+ micromark-util-character: 2.1.1
5437
+ micromark-util-symbol: 2.0.1
5438
+ micromark-util-types: 2.0.2
5439
+
5440
+ micromark-extension-gfm-tagfilter@2.0.0:
5441
+ dependencies:
5442
+ micromark-util-types: 2.0.2
5443
+
5444
+ micromark-extension-gfm-task-list-item@2.1.0:
5445
+ dependencies:
5446
+ devlop: 1.1.0
5447
+ micromark-factory-space: 2.0.1
5448
+ micromark-util-character: 2.1.1
5449
+ micromark-util-symbol: 2.0.1
5450
+ micromark-util-types: 2.0.2
5451
+
5452
+ micromark-extension-gfm@3.0.0:
5453
+ dependencies:
5454
+ micromark-extension-gfm-autolink-literal: 2.1.0
5455
+ micromark-extension-gfm-footnote: 2.1.0
5456
+ micromark-extension-gfm-strikethrough: 2.1.0
5457
+ micromark-extension-gfm-table: 2.1.1
5458
+ micromark-extension-gfm-tagfilter: 2.0.0
5459
+ micromark-extension-gfm-task-list-item: 2.1.0
5460
+ micromark-util-combine-extensions: 2.0.1
5461
+ micromark-util-types: 2.0.2
5462
+
5463
+ micromark-extension-math@3.1.0:
5464
+ dependencies:
5465
+ '@types/katex': 0.16.8
5466
+ devlop: 1.1.0
5467
+ katex: 0.16.47
5468
+ micromark-factory-space: 2.0.1
5469
+ micromark-util-character: 2.1.1
5470
+ micromark-util-symbol: 2.0.1
5471
+ micromark-util-types: 2.0.2
5472
+
5473
+ micromark-factory-destination@2.0.1:
5474
+ dependencies:
5475
+ micromark-util-character: 2.1.1
5476
+ micromark-util-symbol: 2.0.1
5477
+ micromark-util-types: 2.0.2
5478
+
5479
+ micromark-factory-label@2.0.1:
5480
+ dependencies:
5481
+ devlop: 1.1.0
5482
+ micromark-util-character: 2.1.1
5483
+ micromark-util-symbol: 2.0.1
5484
+ micromark-util-types: 2.0.2
5485
+
5486
+ micromark-factory-space@2.0.1:
5487
+ dependencies:
5488
+ micromark-util-character: 2.1.1
5489
+ micromark-util-types: 2.0.2
5490
+
5491
+ micromark-factory-title@2.0.1:
5492
+ dependencies:
5493
+ micromark-factory-space: 2.0.1
5494
+ micromark-util-character: 2.1.1
5495
+ micromark-util-symbol: 2.0.1
5496
+ micromark-util-types: 2.0.2
5497
+
5498
+ micromark-factory-whitespace@2.0.1:
5499
+ dependencies:
5500
+ micromark-factory-space: 2.0.1
5501
+ micromark-util-character: 2.1.1
5502
+ micromark-util-symbol: 2.0.1
5503
+ micromark-util-types: 2.0.2
5504
+
5505
+ micromark-util-character@2.1.1:
5506
+ dependencies:
5507
+ micromark-util-symbol: 2.0.1
5508
+ micromark-util-types: 2.0.2
5509
+
5510
+ micromark-util-chunked@2.0.1:
5511
+ dependencies:
5512
+ micromark-util-symbol: 2.0.1
5513
+
5514
+ micromark-util-classify-character@2.0.1:
5515
+ dependencies:
5516
+ micromark-util-character: 2.1.1
5517
+ micromark-util-symbol: 2.0.1
5518
+ micromark-util-types: 2.0.2
5519
+
5520
+ micromark-util-combine-extensions@2.0.1:
5521
+ dependencies:
5522
+ micromark-util-chunked: 2.0.1
5523
+ micromark-util-types: 2.0.2
5524
+
5525
+ micromark-util-decode-numeric-character-reference@2.0.2:
5526
+ dependencies:
5527
+ micromark-util-symbol: 2.0.1
5528
+
5529
+ micromark-util-decode-string@2.0.1:
5530
+ dependencies:
5531
+ decode-named-character-reference: 1.3.0
5532
+ micromark-util-character: 2.1.1
5533
+ micromark-util-decode-numeric-character-reference: 2.0.2
5534
+ micromark-util-symbol: 2.0.1
5535
+
5536
+ micromark-util-encode@2.0.1: {}
5537
+
5538
+ micromark-util-html-tag-name@2.0.1: {}
5539
+
5540
+ micromark-util-normalize-identifier@2.0.1:
5541
+ dependencies:
5542
+ micromark-util-symbol: 2.0.1
5543
+
5544
+ micromark-util-resolve-all@2.0.1:
5545
+ dependencies:
5546
+ micromark-util-types: 2.0.2
5547
+
5548
+ micromark-util-sanitize-uri@2.0.1:
5549
+ dependencies:
5550
+ micromark-util-character: 2.1.1
5551
+ micromark-util-encode: 2.0.1
5552
+ micromark-util-symbol: 2.0.1
5553
+
5554
+ micromark-util-subtokenize@2.1.0:
5555
+ dependencies:
5556
+ devlop: 1.1.0
5557
+ micromark-util-chunked: 2.0.1
5558
+ micromark-util-symbol: 2.0.1
5559
+ micromark-util-types: 2.0.2
5560
+
5561
+ micromark-util-symbol@2.0.1: {}
5562
+
5563
+ micromark-util-types@2.0.2: {}
5564
+
5565
+ micromark@4.0.2:
5566
+ dependencies:
5567
+ '@types/debug': 4.1.13
5568
+ debug: 4.4.3
5569
+ decode-named-character-reference: 1.3.0
5570
+ devlop: 1.1.0
5571
+ micromark-core-commonmark: 2.0.3
5572
+ micromark-factory-space: 2.0.1
5573
+ micromark-util-character: 2.1.1
5574
+ micromark-util-chunked: 2.0.1
5575
+ micromark-util-combine-extensions: 2.0.1
5576
+ micromark-util-decode-numeric-character-reference: 2.0.2
5577
+ micromark-util-encode: 2.0.1
5578
+ micromark-util-normalize-identifier: 2.0.1
5579
+ micromark-util-resolve-all: 2.0.1
5580
+ micromark-util-sanitize-uri: 2.0.1
5581
+ micromark-util-subtokenize: 2.1.0
5582
+ micromark-util-symbol: 2.0.1
5583
+ micromark-util-types: 2.0.2
5584
+ transitivePeerDependencies:
5585
+ - supports-color
5586
+
5587
  mimic-fn@4.0.0: {}
5588
 
5589
  minipass@7.1.2: {}
 
5678
  degenerator: 5.0.1
5679
  netmask: 2.1.1
5680
 
5681
+ parse-entities@4.0.2:
5682
+ dependencies:
5683
+ '@types/unist': 2.0.11
5684
+ character-entities-legacy: 3.0.0
5685
+ character-reference-invalid: 2.0.1
5686
+ decode-named-character-reference: 1.3.0
5687
+ is-alphanumerical: 2.0.1
5688
+ is-decimal: 2.0.1
5689
+ is-hexadecimal: 2.0.1
5690
+
5691
+ parse5@7.3.0:
5692
+ dependencies:
5693
+ entities: 6.0.1
5694
+
5695
  path-key@3.1.1: {}
5696
 
5697
  path-key@4.0.0: {}
 
5742
 
5743
  progress@2.0.3: {}
5744
 
5745
+ property-information@7.2.0: {}
5746
+
5747
  proxy-agent@6.5.0:
5748
  dependencies:
5749
  agent-base: 7.1.4
 
5801
 
5802
  react-is@19.1.1: {}
5803
 
5804
+ react-markdown@10.1.0(@types/react@19.1.10)(react@19.1.1):
5805
+ dependencies:
5806
+ '@types/hast': 3.0.4
5807
+ '@types/mdast': 4.0.4
5808
+ '@types/react': 19.1.10
5809
+ devlop: 1.1.0
5810
+ hast-util-to-jsx-runtime: 2.3.6
5811
+ html-url-attributes: 3.0.1
5812
+ mdast-util-to-hast: 13.2.1
5813
+ react: 19.1.1
5814
+ remark-parse: 11.0.0
5815
+ remark-rehype: 11.1.2
5816
+ unified: 11.0.5
5817
+ unist-util-visit: 5.1.0
5818
+ vfile: 6.0.3
5819
+ transitivePeerDependencies:
5820
+ - supports-color
5821
+
5822
  react-redux@9.2.0(@types/react@19.1.10)(react@19.1.1)(redux@5.0.1):
5823
  dependencies:
5824
  '@types/use-sync-external-store': 0.0.6
 
5888
 
5889
  redux@5.0.1: {}
5890
 
5891
+ rehype-katex@7.0.1:
5892
+ dependencies:
5893
+ '@types/hast': 3.0.4
5894
+ '@types/katex': 0.16.8
5895
+ hast-util-from-html-isomorphic: 2.0.0
5896
+ hast-util-to-text: 4.0.2
5897
+ katex: 0.16.47
5898
+ unist-util-visit-parents: 6.0.2
5899
+ vfile: 6.0.3
5900
+
5901
+ remark-gfm@4.0.1:
5902
+ dependencies:
5903
+ '@types/mdast': 4.0.4
5904
+ mdast-util-gfm: 3.1.0
5905
+ micromark-extension-gfm: 3.0.0
5906
+ remark-parse: 11.0.0
5907
+ remark-stringify: 11.0.0
5908
+ unified: 11.0.5
5909
+ transitivePeerDependencies:
5910
+ - supports-color
5911
+
5912
+ remark-math@6.0.0:
5913
+ dependencies:
5914
+ '@types/mdast': 4.0.4
5915
+ mdast-util-math: 3.0.0
5916
+ micromark-extension-math: 3.1.0
5917
+ unified: 11.0.5
5918
+ transitivePeerDependencies:
5919
+ - supports-color
5920
+
5921
+ remark-parse@11.0.0:
5922
+ dependencies:
5923
+ '@types/mdast': 4.0.4
5924
+ mdast-util-from-markdown: 2.0.3
5925
+ micromark-util-types: 2.0.2
5926
+ unified: 11.0.5
5927
+ transitivePeerDependencies:
5928
+ - supports-color
5929
+
5930
+ remark-rehype@11.1.2:
5931
+ dependencies:
5932
+ '@types/hast': 3.0.4
5933
+ '@types/mdast': 4.0.4
5934
+ mdast-util-to-hast: 13.2.1
5935
+ unified: 11.0.5
5936
+ vfile: 6.0.3
5937
+
5938
+ remark-stringify@11.0.0:
5939
+ dependencies:
5940
+ '@types/mdast': 4.0.4
5941
+ mdast-util-to-markdown: 2.1.2
5942
+ unified: 11.0.5
5943
+
5944
  require-directory@2.1.1: {}
5945
 
5946
  reselect@5.1.1: {}
 
6049
  source-map@0.6.1:
6050
  optional: true
6051
 
6052
+ space-separated-tokens@2.0.2: {}
6053
+
6054
  stackback@0.0.2: {}
6055
 
6056
  std-env@3.9.0: {}
 
6072
  is-fullwidth-code-point: 3.0.0
6073
  strip-ansi: 6.0.1
6074
 
6075
+ stringify-entities@4.0.4:
6076
+ dependencies:
6077
+ character-entities-html4: 2.1.0
6078
+ character-entities-legacy: 3.0.0
6079
+
6080
  strip-ansi@6.0.1:
6081
  dependencies:
6082
  ansi-regex: 5.0.1
 
6087
  dependencies:
6088
  js-tokens: 9.0.1
6089
 
6090
+ style-to-js@1.1.21:
6091
+ dependencies:
6092
+ style-to-object: 1.0.14
6093
+
6094
+ style-to-object@1.0.14:
6095
+ dependencies:
6096
+ inline-style-parser: 0.2.7
6097
+
6098
  styled-jsx@5.1.6(react@19.1.1):
6099
  dependencies:
6100
  client-only: 0.0.1
 
6163
 
6164
  tinyspy@2.2.1: {}
6165
 
6166
+ trim-lines@3.0.1: {}
6167
+
6168
+ trough@2.2.0: {}
6169
+
6170
  tslib@2.8.1: {}
6171
 
6172
  tsx@4.21.0:
 
6188
 
6189
  undici-types@6.21.0: {}
6190
 
6191
+ unified@11.0.5:
6192
+ dependencies:
6193
+ '@types/unist': 3.0.3
6194
+ bail: 2.0.2
6195
+ devlop: 1.1.0
6196
+ extend: 3.0.2
6197
+ is-plain-obj: 4.1.0
6198
+ trough: 2.2.0
6199
+ vfile: 6.0.3
6200
+
6201
+ unist-util-find-after@5.0.0:
6202
+ dependencies:
6203
+ '@types/unist': 3.0.3
6204
+ unist-util-is: 6.0.1
6205
+
6206
+ unist-util-is@6.0.1:
6207
+ dependencies:
6208
+ '@types/unist': 3.0.3
6209
+
6210
+ unist-util-position@5.0.0:
6211
+ dependencies:
6212
+ '@types/unist': 3.0.3
6213
+
6214
+ unist-util-remove-position@5.0.0:
6215
+ dependencies:
6216
+ '@types/unist': 3.0.3
6217
+ unist-util-visit: 5.1.0
6218
+
6219
+ unist-util-stringify-position@4.0.0:
6220
+ dependencies:
6221
+ '@types/unist': 3.0.3
6222
+
6223
+ unist-util-visit-parents@6.0.2:
6224
+ dependencies:
6225
+ '@types/unist': 3.0.3
6226
+ unist-util-is: 6.0.1
6227
+
6228
+ unist-util-visit@5.1.0:
6229
+ dependencies:
6230
+ '@types/unist': 3.0.3
6231
+ unist-util-is: 6.0.1
6232
+ unist-util-visit-parents: 6.0.2
6233
+
6234
  update-browserslist-db@1.1.3(browserslist@4.25.2):
6235
  dependencies:
6236
  browserslist: 4.25.2
 
6265
  - '@types/react'
6266
  - '@types/react-dom'
6267
 
6268
+ vfile-location@5.0.3:
6269
+ dependencies:
6270
+ '@types/unist': 3.0.3
6271
+ vfile: 6.0.3
6272
+
6273
+ vfile-message@4.0.3:
6274
+ dependencies:
6275
+ '@types/unist': 3.0.3
6276
+ unist-util-stringify-position: 4.0.0
6277
+
6278
+ vfile@6.0.3:
6279
+ dependencies:
6280
+ '@types/unist': 3.0.3
6281
+ vfile-message: 4.0.3
6282
+
6283
  victory-vendor@37.3.6:
6284
  dependencies:
6285
  '@types/d3-array': 3.2.1
 
6359
  - supports-color
6360
  - terser
6361
 
6362
+ web-namespaces@2.0.1: {}
6363
+
6364
  webdriver-bidi-protocol@0.4.1: {}
6365
 
6366
  which@2.0.2:
 
6406
  yocto-queue@1.2.1: {}
6407
 
6408
  zod@3.25.67: {}
6409
+
6410
+ zwitch@2.0.4: {}