Argus

Elevator pitch: Live debate → real-time claim–evidence graph.


Inspiration

Debates move fast. The logic underneath — what's a claim, what evidence was offered, what actually counters what — usually stays trapped in people's heads. Judges and audiences hear rhetoric; they don't see structure.

We wanted the opposite of another chatbot. We wanted a stage moment: two people talk, and a living map of the argument builds itself — with zero seat-clicks, zero speaker toggles, zero "paste the transcript later."

That meant treating Gemini as a structured reasoning engine, not a chat box: extract claims, attach speaker-provided evidence, link counters and responses, then score the graph of the debate — not declare who's "right."

What it does

Argus listens to a live, two-speaker debate in one browser and turns speech into a real-time claim–evidence graph.

  1. Speakers hit Open the floor and talk — no manual turn control.
  2. Audio is chunked via MediaRecorder and sent to Gemini for STT + speaker diarization (A / B).
  3. Transcript windows hit /api/extract, which returns deltas:
    • Claims (graph nodes) — argument or counterargument
    • Evidence (attached, never nodes) — statistics, citations, examples, etc.
    • Relationscounters or responds_to between claims only
  4. A force-directed graph animates claim nodes and relations live. Click a claim → inspector shows speaker, nature, attached evidence, sources, fallacies, and linked claims.
  5. Evidence is corroborated asynchronously via Gemini + Google Search (/api/verify-evidence) — without blocking the live graph.
  6. A deterministic debate score (scoreA / scoreB) updates who is structurally ahead, plus an end-of-debate summary with stats and narrative.

Core ontology rule (the "Messi test"):
"Messi is better because he won a World Cup…"one claim node + one attached evidence item — never two claim nodes glued by a fake "supports" edge.

Argus never labels claims true / false. Language stays structural: unsupported, pending confirmation, sources corroborate / contest.

How we built it

Stack

Next.js 16 (App Router) · React 19 · TypeScript · Tailwind v4 · MediaRecorder · @google/genai (Gemini 3 Flash) · Zod · react-force-graph-2d · Vitest · Vercel

Pipeline

Mic → /api/transcribe (STT + diarization)
    → /api/extract (claims + evidence + relations + soft fallacies)
    → async /api/verify-evidence (Google Search, two-pass)
    → /api/score (pure graph math) + /api/summary
    → live claim graph + momentum UI

Backend surfaces

Endpoint Role
POST /api/transcribe Gemini audio STT + A/B diarization
POST /api/extract Structured deltas; one-call extract + speaker + fallacy tags
POST /api/verify-evidence Async two-pass Search corroboration (never on extract hot path)
POST /api/score Deterministic who-is-ahead score — no API key
POST /api/summary Stats + narrative + embedded debateScore

Deterministic scoring (structure, not truth)

Winning means stronger argument structure + evidence quality signals, not claim truth.

For each claim (c) with attached evidence contribution (E(c)) and soft penalties (P(c)):

[ S_{\text{claim}}(c) = B(c) + E(c) + P(c) ]

Evidence unit before split across supported claims:

[ V(v) = w_{\text{ver}}(v) \cdot w_{\text{rel}}(v) \cdot 1.5 ]

Relation moves credit the speaker of from: counters (+2), responds_to (+1), plus rebuttal/undercut when attacking unsupported opponent claims. Raw speaker totals floor-shift into non-negative masses, then:

[ \mathrm{scoreA} + \mathrm{scoreB} = 100,\quad \mathrm{isDecisive} \iff \mathrm{leaderShare} \ge 0.62 ]

Full formula + worked proofs: docs/DEBATE_SCORING.md.

Frontend

Client session state holds claims / evidence / relations, merges extract deltas by id, serializes a verify queue (concurrency 1), and drives momentum from /api/score. Graph nodes are claims only; evidence lives in badges + Claim Inspector.

Challenges we ran into

1. Claim vs evidence separation. Naive extractors turn every fact into a node. Fixing the "Messi double-node" bug required a strict ontology, prompt rules, merge semantics, and FE acceptance tests so justifications never become graph nodes.

2. Automatic speakers with no toggle. Diarization + extract-time inference is harder than a spacebar seat switch — and overconfident wrong labels kill a demo. We hedge confidence in the UI and fall back to low-confidence heuristics on weak model signal.

3. Latency vs live feel. Mic chunks (~4s) + model time fight the "wow" cadence. We debounce extract (~3s / char threshold), return deltas only, and keep verify off the hot path so the graph never freezes waiting for Search.

4. Grounding + JSON schema. Google Search grounding and strict JSON on one call can silently drop sources. Verify uses a two-pass design: grounded prose first, then structured JSON against allowlisted sources only — corroborated requires ≥1 real source.

5. Scoring without becoming a fact-checker. Judges need a clear "who's ahead," but we refuse claim true/false labels. The score is pure graph math over nature, evidence verification/relevance, unsupported penalties, fallacies, and relation credits — testable and deterministic.

Accomplishments that we're proud of

  • A full live vertical slice: talk → graph grows → inspector → async corroboration → who-is-ahead score.
  • A clean claim–evidence–relation contract with FE handoff docs, fixtures, and backend tests.
  • Two-pass Search verify that never blocks extraction, with honest statuses (corroborated / contested / inconclusive / not_verifiable).
  • A deterministic scoring engine with documented invariants (scoreA + scoreB === 100, evidence never scored as a claim, UNKNOWN speakers contribute 0).
  • Soft fallacy tags and confidence-aware speaker labels — warnings, not gotchas.
  • A polished debate-floor UI where the lit moment is obvious: structure appears as people speak.

What we learned

  • Structured extraction is a product problem, not just a prompt: ontology, IDs, merge rules, and UI must agree.
  • Separating speaker support (did they offer evidence?) from external corroboration (do sources align?) keeps the demo honest.
  • For live demos, hedging beats false certainty — especially on speaker labels.
  • Async side paths (verify) are what let AI features feel instant.
  • Deterministic math on top of model output makes "who's winning" explainable and demo-safe.

What's next for Argus

  • Soft score influence from corroboration beyond provisional pending weights
  • Live transcript sync (click claim → originating sentence)
  • Replay mode: animate the full graph build from (t = 0)
  • Steelman Mode: strongest version of the opposing argument
  • Topic clustering / post-hoc speaker re-labeling
  • Deploy hardening for shared demo keys and production smoke on the rehearsal script

Repo: github.com/skhdemo/Argus (develop)
Docs: PRD.md · DEBATE_SCORING.md · FRONTEND_HANDOFF.md

Built With

Share this project:

Updates