Support ticket triage
An online shop routes every incoming ticket to one of four teams. A misrouted ticket waits in the wrong queue and gets passed along. When jev-latest moves to a new version, the probabilities move overnight.
“Which team should handle this ticket?”
The request · POST /v1/systemone
{
"model": "jev-latest",
"state": {
"subject": "Where is my order?",
"body": "…"
},
"questions": {
"team": {
"type": "choice",
"instructions": "Which team should handle this ticket?",
"criteria": {
"billing": "…",
"shipping": "…",
"returns": "…",
"tech": "…"
}
}
}
}
The policy
- top option ≥ tSELECT:<team>route it to that team
- otherwiseESCALATEa human dispatcher decides
Misroutes ≤ 25% among auto-routed tickets, with 95% confidence.
t = 0.65 in one run of the demo, on generated data, proposed from 2,166 tuning tickets. On 1,088 tickets it never saw, 55.3% were routed without a person and 18.3% of those went to the wrong team (95% interval 15.2% to 21.7%). The generated model is wrong about a third of the time, which is why the target is 25%; a better model supports a tighter one. A policy is bound to the exact model version, so a new version behind jev-latest gets the default until it is refit.
When the truth arrives
- nowRouted to a team, or escalated.proxy
- hoursThe team that finally closed the ticket, from the help desk.downstream
- 72 hoursNo reassignment: the first routing was right.rule
In your app · Python SDK, gate() from M3
d = ts.gate("team", answer=resp["answers"]["team"],
model_served=resp["model"], decision_id=ids[0])
if d.action.startswith("SELECT:"):
route(ticket, team=d.action.removeprefix("SELECT:"))
else:
dispatcher_queue.add(ticket)
Run the demo from a clean checkout: a month of tickets end in a compiled policy that a person approves. An app using the Python SDK picks it up and routes six tickets locally. A second policy goes live and is rolled back while the app is watching, and the audit log keeps who did what and why.
Run the demo