AI-assisted service-desk ticket triage with a human in the loop. A user submits a ticket; Claude classifies its category, priority (P1–P4), and team, writes a one-sentence summary, and reports a confidence score. A human reviewer approves or overrides every suggestion. Every action lands in an audit trail, and the dashboard shows three honest numbers: total tickets, override rate (is the AI earning trust?), and average confidence.
git clone <this repo> && cd triagedesk
set ANTHROPIC_API_KEY=sk-ant-... # PowerShell: $env:ANTHROPIC_API_KEY = "sk-ant-..."
dotnet run --project app -- seed # load 17 realistic demo tickets
dotnet run --project app # http://localhost:5000 (port printed on startup)
Tests (LLM always faked, temp database): dotnet test tests
No API key? Everything still works — triage degrades to needs_review with confidence 0,
and the human does the classification. That failure mode is deliberate.
Browser (server-rendered HTML, zero JS)
│
▼
ASP.NET Core minimal API — one process (app/)
│ ╲ one HTTPS call per new ticket
▼ ▼
SQLite file (app.db, two tables) Claude API (claude-opus-4-8, schema-enforced JSON)
~600 lines of C#. Program.cs routes, Db.cs SQLite helpers, Triage.cs the one LLM call,
Html.cs the three pages, prompts/triage.txt the prompt. Tickets with confidence < 0.70
are flagged and sorted to the top of the review queue — that's the user-in-the-loop.
| Feature | Why not now | When it's justified |
|---|---|---|
| Postgres / SQL Server | SQLite handles one demo user perfectly | More than one concurrent writer, or a real deployment |
| Auth / SSO | Single-user demo; decided_by = "demo-user" |
The moment a second real user exists |
| Background jobs / queue | Synchronous LLM call returns in ~2–3 s | Throughput or reliability SLAs |
| RAG / knowledge base | Classification needs no retrieval | Adding a "suggested resolution" feature |
| Multi-agent orchestration | One well-designed prompt does this job | Genuinely independent subtasks that must run in parallel |
| ServiceNow / email connectors | Seed JSON demonstrates the flow | A pilot with a real ticket source |
| React / any JS framework | Two pages of forms and tables | Interactivity server-rendered HTML can't do |
| Docker / K8s / CI pipeline | Runs from one dotnet run |
A second machine or a teammate |
| LLM provider abstraction layer | One provider, one function | An actual need to swap providers |
| Charting library | Three numbers tell the story | A stakeholder asks for trends over time |