Reasoning Tokens: Why o1 Bills for Text You Never See
9 min read · updated August 11, 2026
A 300-word answer from o1 can arrive with 5,000 output tokens on the bill. Nothing is wrong. The model generated thousands of tokens of reasoning before writing the answer, and those tokens are billed at the output rate and discarded before the response is returned.
Where they appear
The API tells you exactly how many, in a nested field on the usage object:
"usage": {
"prompt_tokens": 1200,
"completion_tokens": 4400,
"total_tokens": 5600,
"completion_tokens_details": {
"reasoning_tokens": 4000,
"accepted_prediction_tokens": 0,
"rejected_prediction_tokens": 0
}
}The containment relationship is the thing to get right, because reading it wrong doubles or halves every cost estimate you make:
completion_tokens = reasoning_tokens + visible answer tokens
4400 = 4000 + 400
total_tokens = prompt_tokens + completion_tokens
5600 = 1200 + 4400Reasoning tokens are a subset of completion tokens, not an addition to them. If you are computing cost as prompt + completion + reasoning you are counting the reasoning twice. The visible answer is completion_tokens minus reasoning_tokens — 400 tokens here, roughly 300 words, against 4,400 billed.
You cannot see the reasoning text itself. OpenAI returns a count and not the content, so there is no way to audit what those 4,000 tokens contained. The reasoning is also dropped from the conversation once the response completes, which means you are not billed for it again on the next turn — the mechanism is described in o1’s context window.
What they cost
Reasoning tokens are billed at the model’s output token rate. There is no separate reasoning rate and no discount: as far as the meter is concerned, a reasoning token and an answer token are the same thing. Prices per model are on OpenAI’s pricing page, and that is the only figure to trust.
A worked invoice
Take the usage object above — 1,200 prompt tokens, 4,000 reasoning tokens, 400 visible answer tokens — and price it.
assumptions (o1 rate at time of writing): input $15.00 per 1,000,000 tokens output $60.00 per 1,000,000 tokens input: 1,200 × 15.00 / 1,000,000 = $0.0180 output (reasoning + visible, billed together): 4,400 × 60.00 / 1,000,000 = $0.2640 total for one request = $0.2820
Now split that output line to see where the money went:
reasoning 4,000 × 60.00 / 1,000,000 = $0.2400 (85% of the bill) visible 400 × 60.00 / 1,000,000 = $0.0240 ( 9% of the bill) input 1,200 × 15.00 / 1,000,000 = $0.0180 ( 6% of the bill)
Eighty-five per cent of the cost of that request bought text nobody will ever read. And the ratio to reason about is not cost per token but cost per delivered token:
effective rate on visible output:
$0.2640 of output charges / 400 visible tokens
= $0.00066 per visible token
= $660 per million visible tokens
against a nominal $60 per million output tokens — an 11× multiplier,
which is exactly the ratio completion_tokens / visible tokens.That multiplier is the number to carry into any capacity plan. If you budgeted a reasoning model at its posted output rate and your traffic runs at a ten-to-one reasoning ratio, your forecast is out by an order of magnitude. At a thousand such requests a day the example above is about $282 daily, of which $240 is reasoning.
Why the number moves
Reasoning token counts are not a property of the model you can look up. They vary per request, and the variation is large.
- Problem difficulty. The model spends more on harder problems. That is the entire design. A trivial question may use a few hundred reasoning tokens; a genuinely hard one can use tens of thousands.
- Ambiguity. An underspecified prompt gives the model more to consider. Tightening a prompt reduces reasoning spend as a side effect of reducing the space of interpretations.
- The same prompt, twice. Reasoning is sampled like anything else, so two identical requests can produce materially different reasoning counts and therefore different bills. There is no parameter that pins this — see the seed parameter.
The operational consequence is that a per-request cost estimate from a reasoning model is a distribution, not a number. Track the p95 of reasoning_tokens for each of your prompt templates, not the mean: the mean is what you pay on average and the p95 is what breaks your budget alert.
The worst version of this is the request that bills for reasoning and returns nothing. Set a tight max_completion_tokens, give the model a hard problem, and the entire budget can go into reasoning before a single visible token is emitted:
"choices": [{"message": {"role": "assistant", "content": ""},
"finish_reason": "length"}],
"usage": {
"prompt_tokens": 1200,
"completion_tokens": 800,
"completion_tokens_details": {"reasoning_tokens": 800}
}
billed: 800 × $60 / 1,000,000 = $0.048
returned: nothingHTTP 200, empty string, non-zero charge. A client that treats empty content as a transient glitch and retries with identical parameters will reproduce it exactly, at the same price, indefinitely — this is how a retry loop turns a configuration mistake into a bill. The check that catches it is the pair: finish_reason of "length" together with reasoning_tokens close to completion_tokens means the budget was consumed by thinking, and the correct response is a larger budget rather than another attempt. The window mechanics behind it are in o1’s context window.
Streaming needs one extra step to see any of this. A streamed response carries no usage object by default, so reasoning_tokens — the field that accounts for most of what you are spending — is simply absent unless you ask for it with "stream_options": {"include_usage": true}. It then arrives in a final chunk whose choices array is empty, which is a shape that breaks clients written before the option was turned on. Both details are in the streaming chunk format, and the practical consequence is specific: a team that streams and never enabled usage reporting has no per-request record of its largest cost line, and will be reconstructing it from the invoice.
What you can control
- Use the reasoning-effort setting. Where the model exposes low, medium and high effort levels, this is the direct lever on reasoning spend. Low effort on a classification task can cut the reasoning count by a large factor at no cost to accuracy, because the task did not need deliberation in the first place.
- Do not use a reasoning model for non-reasoning work. Extraction, summarisation, formatting, classification and routing are tasks where a non-reasoning model is both cheaper per token and spends nothing on reasoning at all. The compound saving is much larger than the headline price difference suggests.
- Set max_completion_tokens generously, not tightly. Unused budget is free — you are billed for tokens generated, not tokens allowed. A tight limit does not save money; it buys you a truncated or empty response that you paid for anyway and then have to retry. The failure mode is in the default max token behaviour.
- Log reasoning_tokens on every request. It is the only visibility you get into the invisible half of the bill, it is free to record, and without it a cost regression from a prompt change is undiagnosable.