Research · Methodology Report

OpenVoiceCS-Bench: Measuring Whether an Agent Actually Resolved the Call

220 synthetic customer-service scenarios, eight deterministic metrics scored from a replayable trace, and a 52-model leaderboard on the text-to-action track. This report covers how the benchmark works, what keeps the scoring honest, and the limitations we publish next to the numbers.

View the leaderboard → Code & data on GitHub
Not peer-reviewed, and not a finished voice-agent leaderboard. Only one of the five tracks has model data, one metric is provisional, and there are no confidence intervals. The limitations section is part of the result.
220 scenarios, one swept track Five tracks cover text, robustness, adversarial compliance, audio, and voice transport. Only text_to_action (69 scenarios × 3 trials) has a model sweep.
Deterministic, replayable scoring Tool calls are replayed against a scenario-local state copy. Same trace in, same score out. The oracle agent passes 220/220 by construction.
A failure to measure is not a measurement Infrastructure failures are never scored as zeros. Models below 90% trial coverage are listed as unmeasured, not ranked.
What to trust The podium is stable; the mid-table is not. Grounding is provisional, there are no confidence intervals, and the no-op floor is 24.89.
01 · Summary

Resolution, Not Vibes

Most voice-agent evaluation asks whether the agent sounded helpful. OpenVoiceCS-Bench asks whether it actually resolved the customer’s problem without breaking policy — and makes it prove that with a replayable trace. Every scenario defines a goal, an initial system state, a set of replayable tools, and a standard operating procedure; every score is computed deterministically from what the agent actually did, not from what a judge felt about it.

The leaderboard ranks 52 of 58 attempted models on the text_to_action track. The spread is real: overall scores run from 25.38 to 88.87, and task_success — did the customer’s problem actually get resolved — runs from 0.010 to 0.754. Even the leader fails a quarter of scenarios.

The rest of this report is the methodology: what the scenarios contain, how replay scoring works, the rules that keep failure signals about the model rather than the harness, and the limitations we publish next to the numbers instead of hiding behind them.

Read this as a text-track result plus a validity report. It is not a finished voice-agent leaderboard: four of the five tracks have no model data yet, one of the eight metrics is provisional, and one sweep of three trials carries no confidence intervals.
02 · Corpus & Metrics

What The Benchmark Measures

The corpus is 220 synthetic scenarios across five tracks. All data is synthetic — no real customer records, no real personal data, no recordings of real people. Six domains carry the load — retail (38), travel (38), fintech sandbox (37), telecom (36), healthcare admin (35), and SaaS support (35), plus a single utility-support scenario — with 120 TTS-generated audio variants. The corpus splits into public-dev (99 scenarios) for development and reproduction and sealed-test (121 scenarios) that is never published; split commitments publish counts and hashes without revealing sealed IDs.

Figure 1Five tracks, 220 scenarios — one track has model data
text_to_actionCore resolution and tool use from a text transcript
69
52-model sweep
robustnessDisfluencies and self-corrections within an utterance
51
No model data yet
adversarial_complianceSocial engineering, impersonation, injection, PHI extraction
45
No model data yet
audio_to_actionDirect audio input to correct action
35
No model data yet
end_to_end_voiceVoice-transport delivery of a single exchange
20
No model data yet
Only text_to_action has a provider sweep (69 scenarios × 3 trials per model). Nothing on this page or the leaderboard says anything about how models behave on the other four tracks.

Each trace is scored on eight deterministic metrics, combined into an overall score out of 100 with fixed weights:

Figure 2Eight metrics and their fixed weights
task_success
Did the customer’s actual problem get resolved?
0.20
factual_groundingprovisional
Were claims grounded in retrieved state rather than invented?
0.20
sop_compliance
Was the standard operating procedure followed?
0.18
tool_correctness
Right tools, right arguments, valid order?
0.17
auth_integrity
Was identity verified before privileged actions?
0.10
privacy
Was PII minimized and disclosure limited to the verified party?
0.10
safety
Were forbidden actions refused?
0.03
experience_proxy
A deterministic proxy for conversational quality
0.02
factual_grounding is provisional — it is still a literal phrase matcher. See limitations before reading anything into mid-table ordering.

Alongside the metrics, every report carries the operational evidence that decides whether an agent is deployable at all: per-turn latency percentiles, tool-call efficiency, token cost, flake rate across trials, and measurement coverage.

03 · Mechanism

How Scoring Works

A scenario is a contract. It defines the customer’s goal, the initial state of the backing systems, a set of replayable tools — each with preconditions and state effects — and the standard operating procedure the agent is supposed to follow. The agent produces a trace: its messages, its tool calls, and the policy events those triggered.

Figure 3From scenario to score — every step deterministic
1 Scenario contract Goal · initial state · replayable tools · standard operating procedure
2 Agent produces a trace Messages · tool calls · the policy events they trigger
3 Deterministic replay Every call re-executed against a scenario-local state copy; preconditions checked against what the state actually was
4 Score Eight metrics computed from the replayed trace → overall / 100. Same trace in, same score out
Subjective quality is handled by a separate, blinded, multi-rater judging pass with adjudication, and reported separately — it never touches these scores.

The anchor for all of this is the oracle agent: a reference agent that performs each scenario correctly by construction. It passes 220 of 220 scenarios, so any oracle regression means the harness broke, not the agent. At the other end, a no-op agent that replies politely and never acts scores 24.89 overall — the floor that makes the scale readable.

Figure 4The scale runs from 24.89, not from zero
24.89 no-op
25.38 lowest ranked
88.87 leader
100 oracle
The usable band is roughly 25–100. “Don’t do harm” metrics are satisfied by inaction, so doing nothing already earns 24.89 — and the lowest-ranked model is statistically indistinguishable from doing nothing at all.

Models are exercised through two collection paths: providers with native tool calling use it directly, and chat-only models run a stepwise JSON action loop bounded to eight rounds, which is what makes the long tail of the OpenRouter catalog scoreable at all.

What failure looks like in practice is usually not spectacular. The most common single cause of a failed scenario, even for the leader, is performing the customer-facing action and then omitting a required piece of secondary bookkeeping:

Most common failure fintech-sandbox-service-action-001
called : verify_identity, perform_service_action(resolution=completed)
missing: create_case(case_id=case_fs_001, reason=card_dispute)
The customer’s dispute was handled; the case record the SOP requires was never created. That is genuine SOP non-compliance — closer to thoroughness than to reasoning, which is part of why this ordering does not mirror reasoning-focused benchmarks.
04 · Validity

Measurement Honesty

The rule underneath everything: a failure to measure is not a measurement. Every failed trial is attributed to either the infrastructure or the model. Rate limits, provider 404s, empty balances, and transport errors are infrastructure: they are excluded from metric means and reported as reduced measurement_coverage. Refusals, malformed actions, and wrong tool calls are the model’s problem: they score what they score.

On top of that classification sits a hard floor: a model is ranked only if at least 90% of its trials produced a usable trace. Six of the 58 attempted models fall below it and are listed as unmeasured — a different statement from “scored badly”. The rule is load-bearing: in early harness runs, before the floor existed, one free-tier model ranked first on the strength of 7% trial coverage — the handful of trials that survived rate limiting happened to go well — and two models whose endpoints returned HTTP 404 for every request ranked at 0.00, as though they had been evaluated and failed everything.

Four rules keep failure signals about the model rather than the harness, and each is pinned by a regression test:

1 Failed trials are attributed, never averaged in

Every failed trial is classified infrastructure or model. Infrastructure failures never enter metric means as zeros; they reduce measurement_coverage, which every report carries and the leaderboard enforces.

2 Safety assertions must be falsifiable

Every declared forbidden event is bound to an observable trigger — 517 bindings across the corpus. A deliberately violating agent fires a forbidden event in 220 of 220 scenarios; the oracle fires none. CI fails if a scenario ever declares an event that nothing can emit.

3 Agents are never scored on values they cannot know

582 argument slots — case IDs, action IDs, resolution codes — are declared system-assigned and excluded from exact matching. An argument stays scored only when its value appears verbatim in content the agent reads.

4 Replay errors are not “safety violations”

Only precondition_failed — acting before a guard was satisfied — counts against safety. Wrong arguments and tool-resolution mistakes are scored by tool_correctness, where they belong. The safety metric can still reach 0.0, and a test asserts that it does.

The six exclusions, with coverage and cause, are published next to the leaderboard rather than in a footnote.

05 · Cost

Token Efficiency

Per-token pricing changes; the number that transfers is how many tokens a system burns to actually resolve something. The leaderboard therefore reports tokens_per_success: total tokens spent, divided by the number of scenarios actually resolved. The denominator is the point. An agent that spends heavily and fails is charged for the budget it burned on those failures, which is exactly how a deployment experiences it.

Figure 5Tokens per resolved scenario — best vs. worst ranked model
claude-fable-5best
9,730
hy3-previewworst
221,504
~23× span across ranked models, at similar-looking overall scores
A success is task_success = 1.0 — deliberately not the stricter all-seven-metrics gate, which the provisional grounding metric would drag around.

The ~23× spread is the deployment-relevant result in this release: two agents with similar-looking overall scores can differ by an order of magnitude in what they cost to run per resolved case.

06 · Conversation

Multi-Turn Conversations

A real support call is a negotiation, not a single utterance. The harness replays conversations turn by turn: the agent is called once per customer turn; later customer turns are withheld, so an agent cannot read the customer’s next objection before answering the current one; the agent’s own prior replies are fed back to it; and state advances between turns, so turn N sees the account exactly as turn N−1 left it. Single-turn scenarios still call the agent exactly once with the scenario untouched.

Figure 6Multi-turn coverage is a pilot, not the corpus
201 scenarios single-turn 19 scenarios multi-turn pilot — verification back-and-forth, cross-turn correction, escalating social engineering, objection handling
Until the bulk of the corpus is re-authored, multi-turn results are pilot results, and end_to_end_voice remains a transport test rather than a duplex one.
07 · Read Before Quoting

Honest Limitations

These are the caveats we would rather list than have a reader discover. Every one is measured against the current repository, not asserted, and each carries a reproduction command in docs/known-limitations.md.

The grounding metric is provisional

factual_grounding is a literal phrase matcher, and it conflates three different things. It misses synonymy: fee_waived accepts “no change fee” and “fee waiver”, but an agent saying “rebooked you at no charge” is marked ungrounded. It correctly catches genuine omissions, like never stating a $12.00 credit amount. And it punishes honest failure reports: where a scenario injects a tool failure and the agent truthfully says “I couldn’t complete this, I’ve escalated it”, the required claim completed is absent and the agent is penalised for accuracy.

The consequence is measured: removing the metric leaves the top three unchanged but moves 40 of 52 models somewhere in the ordering. The podium is trustworthy; fine-grained mid-table ordering is not. A semantic grader to replace this metric is the single most valuable contribution anyone can make to the project.

One sweep, three trials, no confidence intervals

Nothing in this release separates models a couple of points apart. Until repeated sweeps produce intervals, treat a two-point gap as noise. Gaps under a few points are not results, and we ask you not to quote them as results.

One track of five

The sweep covers text_to_action only. robustness, adversarial_compliance, audio_to_action, and end_to_end_voice have no provider sweep, so this is not a voice-agent leaderboard yet — it is a text-track result. There is also no hosted sealed evaluator, so published numbers carry no contamination control.

Tool-call rate is sensitive to cosmetic prompt wording

Holding the model, scenarios, and scorer fixed and changing only how tool arguments are annotated in the prompt:

Figure 7Same model, same scenarios — only the schema annotation changed
Avg tool calls per scenario
No annotation
2.93
“System-assigned” noted
2.29
task_success
No annotation
0.143
“System-assigned” noted
0.357
Two different annotation wordings produced byte-identical behaviour, and authoring real tool descriptions changed nothing (0.357 either way) — so under-documented tools are not the cause. The annotated variant is the fair measurement and is what the published sweep uses.

Marking an argument system-assigned in any wording makes models call the tool less often — a 2.5× swing in task_success from wording alone. Absolute task_success is therefore not stable across harness revisions, and re-scored older runs are not comparable to a fresh sweep.

“Safety” is trivially satisfied by inaction

The no-op baseline — reply politely, never act — scores 0.990 on safety and 24.89 overall. Safety is a don’t-do-harm measure and must be read next to task_success, never quoted alone. The no-op’s 24.89 is also what makes the scale readable (Figure 4): the usable band is roughly 25–100, and the lowest-ranked model at 25.38 is indistinguishable from doing nothing at all.

Smaller prints

Binary trial gating compresses the passed family: a trial passes only when all seven deterministic metrics equal exactly 1.0, so an agent at 0.95 on six metrics records the same as one that crashed — read the per-metric means instead. Latency measures the full JSON action loop, up to eight sequential provider calls, and is not comparable to a single-turn voice latency budget. And the 120 audio variants are TTS-generated from a small speaker set: claims about robustness to real-world audio are not supported by this release.

08 · Reproduce

Check It Yourself

The leaderboard is rebuildable from published artifacts, offline, with no API key. Scoring a model yourself needs an OpenRouter key. Every release artifact is SHA-256 pinned and cross-validated, and CI runs the full verification gate on every push.

# Score one model against the track (needs OPENROUTER_API_KEY)
python scripts/run_openvoicecs.py score-provider \
  --provider openrouter --model google/gemini-2.5-flash-lite \
  --track text_to_action --trials 3 --json-trace --output report.json

# Rebuild the leaderboard from the published reports (offline, no API key)
python scripts/build_leaderboard.py \
  data/openvoicecs/runs/text_action_v02_merged/reports \
  --output /tmp/leaderboard.csv

The full sweep runs unattended on a spot VM, is resumable, and took roughly two hours. Code is Apache 2.0, data is CC BY 4.0, and all of it — scenarios, runs, limitations, regression tests — lives at github.com/0daycloud/openvoicecs-bench.

The ranked table itself, with the excluded models and the reference anchors, is on the results page. Read it with this report beside it — that is what the two pages are for.