← How I Built It
Claude Haiku 4.5

How I built the Email Triage demo

Read an inbound email once, and come out the other side with a category, an urgency level, who should own it, and a draft reply — the four decisions a human triaging a shared inbox actually makes.

Last reviewed

Evidence typeModel demonstrationClaude Haiku 4.5 processes the real email text a visitor submits, live, via the production endpoint; this page's benchmark (8 hand-authored synthetic emails, run 2026-08-02) is reported below, not pre-scripted.

The problem

A shared inbox mixes sales inquiries, support tickets, complaints, spam, and the occasional legal notice. Triage isn't one decision — it's classify, prioritize, route, and often draft a first response, all before anyone with the right context has read the message.

One call, five decisions

Rather than chain separate classify → route → draft calls, the route asks for one JSON object with all five fields at once: category, urgency, sentiment, routing destination, a one-line summary, a suggested reply, and extracted key entities. Fewer round trips, and the fields stay consistent with each other since one call reasons about all of them together.

Every field is a closed enum, not free text

category: Sales | Support | Complaint | Partnership | Spam | Internal | Invoice | Legal

urgency: low | medium | high | critical

sentiment: positive | neutral | negative | frustrated | urgent

routeTo: Sales | Support | Finance | Legal | Management | Spam | HR

Why enums, not open categories

An open-ended "category": string field looks more flexible, but it pushes the hard part downstream: whatever consumes this output — a routing rule, a dashboard filter, a ticketing integration — now has to handle arbitrary strings a model might invent. Naming the exact set of allowed values in the prompt turns validation into a one-line membership check instead of fuzzy string matching against however the model phrased something this time. It's a small constraint that removes an entire category of downstream bugs.

Labeled benchmark

Run 2026-08-02

Model

Claude Haiku 4.5 (claude-haiku-4-5-20251001)

Sample size

8 synthetic emails

Data source

8 hand-authored synthetic emails (complaint, sales inquiry, invoice, security incident, partnership pitch, spam, internal HR note, legal notice) run live against the production endpoint at tioga.ai.

Category exact-match

8/8 (100%)

Urgency exact-match

5/8 (63%)

Successful classifications

8/8 (HTTP 200)

Average latency

~1.8s

Limitations

  • Urgency is inherently more subjective than category — all 3 mismatches were one severity level off (e.g. "high" vs "critical"), and every miss erred toward flagging higher urgency, not lower.
  • Sample size is small (8 cases) and hand-authored; a production engagement would calibrate urgency thresholds against your team's actual triage decisions.
  • Sentiment and routing fields weren't scored in this run — only category and urgency.