Per-Request Speculative-Decoding Metrics
Per-Request Speculative-Decoding Metrics
When an inference server reports per-request speculative-decoding acceptance on each response, AIPerf turns it into an end-of-run Spec Decode console section, the same scalars in the aggregate JSON/CSV, a pooled acceptance histogram in JSON, and per-request values in the records trace. It is engine-agnostic — AIPerf reads a normalized acceptance record and never branches on the engine — and needs no AIPerf flag: the section appears automatically whenever the stats are present, and disappears cleanly when they are not.
There are two ways to get acceptance metrics out of AIPerf; pick by what your server exposes:
- Per-request (this guide): the stats ride the response body, per choice, so AIPerf
reads them inline during a normal
aiperf profilerun. Highest fidelity — you get per-request distributions (avg/min/percentiles) and a pooled histogram. Direct-to-vLLM only. - Server scrape: aggregate acceptance is read from the server’s Prometheus
/metricsendpoint via--server-metricsand assembled withaiperf speed-bench-report. See the SPEED-Bench tutorial for that path and for ready-made datasets.
For the record shape and the adapter that fills it, see Per-Request Speculative-Decoding Acceptance; for the metric definitions and formulas, see the Speculative Decoding Metrics section of the metrics reference.
Prerequisites
- A vLLM server running speculative decoding with per-request stats enabled via
--per-request-spec-decode-stats summary(ordetailed). The field shape tracks vLLM PR #48915 — confirm your vLLM build includes it. - Direct-to-vLLM only. Behind Dynamo the custom stats field is currently stripped, so the per-request path is unavailable there (use the server-scrape path instead).
- Streaming works out of the box; per-request
completion_tokensis only populated when the server also returns usage (enable server token counting if you want it).
Start a vLLM server with per-request spec-decode stats
This example uses a Llama-3.1-8B target with a Llama-3.2-1B draft model and a 5-token draft
budget. --per-request-spec-decode-stats is the flag that makes vLLM attach acceptance
stats to each response choice:
Verify the server is ready:
Run AIPerf
No spec-decode-specific flag is required — run a normal profile. Add --export-level records if you want the per-request acceptance struct in the records trace (see
Per-request trace below):
Reading the output
Console: the Spec Decode section
The end-of-run console gains a dedicated Spec Decode table followed by a one-line pooled acceptance histogram.
The table below is illustrative — it shows the output format, not a benchmark result. The numbers are placeholders; real values depend entirely on your model, drafter, draft budget, dataset, and concurrency.
Quick reading (full definitions in the metrics reference):
- Acceptance Length — tokens emitted per verify step (
j + 1); the headline speed number. Token-Weighted Acceptance Length is the run-level companion that weights every verify step equally instead of every request. - Draft Acceptance Rate — fraction of proposed draft tokens accepted (
j / l); the drafter-quality number. Overall Draft Acceptance Rate is its draft-volume-weighted run-level companion. - Accepted per Verified —
(j + 1) / (l + 1), a[~0, 1]utilization: how close each step got to accepting everything it proposed. - Spec Decode Steps — verify steps per request.
- Accepted-draft histogram — share of verify steps that accepted exactly
jdraft tokens, pooled across the run. Capped to buckets0..7on the console (anyj >= 8folds into a trailing>=8bucket); the full histogram is in the JSON export.
The section is omitted entirely when no request carried spec-decode stats.
Aggregate JSON and CSV
The scalar metrics land in profile_export_aiperf.json and profile_export.csv. The full
pooled histogram is structured, so it goes to JSON only, under
pooled_spec_decode_acceptance_histogram (its counts sum to total_spec_decode_steps):
Per-request trace
At --export-level records, each line of profile_export.jsonl carries the neutral
acceptance struct under spec_decode_acceptance, so the per-request histogram, counts, and (when the
server reports them) per-step arrays travel with the trace:
At --export-level raw, the histogram is already present in the raw response body that raw
export preserves, so no additional field is needed there.
When nothing shows up
If the Spec Decode section, histogram, and spec_decode_* fields are all absent, that is
the expected clean-degradation behavior — not an error. Common causes:
- speculative decoding is off, or the requests had no verify steps;
- the server was not started with
--per-request-spec-decode-stats; - the server is behind Dynamo, which strips the custom field (use the server-scrape path instead);
- the vLLM build predates PR #48915.
See also
- Speculative Decoding Metrics — metric definitions and formulas.
- Per-Request Speculative-Decoding Acceptance — the engine-neutral record and adapter architecture.
- SPEED-Bench tutorial — the server-scrape acceptance path and ready-made speculative-decoding datasets.
- SpecBench tutorial — profiling with the SpecBench speculative-decoding dataset.