Skip to content

Cost and FinOpsAnalysis

Reconcile your AI bill: estimate vs. provider invoice

Your gateway's cost figure is a model of a price list, not a measurement of a charge. The two are rarely compared, and the gap is where an unmodelled rate hides for a quarter.

By INFRO Editorial

Published

Updated

16 min read

A dark operations scene in which two parallel streams of light run side by side and separate slightly, the gap between them widening as they travel

In short

Nearly every AI gateway and observability tool computes cost the same way: it reads the token counts a provider returned, multiplies them by a rate table it maintains, and shows you the product. That is an estimate. It drifts from the invoice through cache pricing, negotiated rates, service tiers, day boundaries and unpriced models — and the only way to know it has drifted is to compare it against the provider's own cost API, which both OpenAI and Anthropic publish. Compare a week at a time, watch the direction rather than any single day, and report the share of requests you could not price at all.

Key takeaways

  • Nearly every cost figure in an AI gateway is a rate table applied to token counts. It is a model of the price list, not a record of the charge.
  • 98% of FinOps practitioners now manage AI spend, up from 63% a year earlier, and visibility into AI cost is the first of the three obstacles they name.
  • Prompt caching is the largest single source of drift: a cache write costs more than a plain input token and a cache read costs far less, so a table that models neither is wrong in both directions at once.
  • OpenAI and Anthropic both publish organization-level cost APIs behind a separate admin credential, and Anthropic lists cost reconciliation as an intended use of its own.
  • The two APIs disagree on units — OpenAI reports dollars as a number, Anthropic reports cents as a decimal string — and reading one as the other is a hundredfold error in a figure nobody sanity-checks.
  • Judge a variance by direction over a week, not by magnitude on a day. One day is timing; five days leaning the same way is a rate you do not model.
  • Report unpriced requests separately. A window containing one has a variance that is partly a coverage gap, and the fix for each is different.

A finance partner asks what the model spend was last month. Somebody opens the gateway dashboard and reads out a number to the cent. Somebody else opens the provider console and reads out a different one. The meeting resolves the way these meetings always resolve — the invoice is the real number, the dashboard is "roughly right", and everyone moves on.

Nobody writes down the gap. Nobody checks whether it was the same gap last month. And because nobody checks, a rate that the dashboard has never modelled correctly can sit there for two quarters, quietly making every per-customer margin figure in the company slightly wrong in the same direction.

This is not an argument that dashboards are bad. It is an argument that a number produced one way and a number produced another way should be compared, and that the comparison is rarely made.

Your cost figure is a model, not a measurement

Nearly every AI gateway and LLM observability tool computes cost the same way. The provider returns token counts on the response. The tool multiplies those counts by a rate it holds in a table. It stores the product and shows it to you. Some upstreams put a cost figure in the response itself; most return only the counts.

That is the whole mechanism. There is no billing feed involved and no charge being observed. What you are looking at is a rate table applied to token counts — a model of the provider's price list, maintained by people who do not work at the provider, evaluated against counts the provider reported for its own purposes.

You can see the shape of this in how the tools describe themselves. Cloudflare AI Gateway lets you enter custom costs, and its documentation says plainly that they "can reflect your negotiated input, output, cache-read, and cache-write rates" and "override the default or public model costs"1. The default, in other words, is a public list rate. The same page notes that a response served from its cache always shows a cost of zero, even when a custom cost is configured1 — a sensible choice, and one more place where the figure on the screen and the figure on the invoice are answering different questions.

None of that is a defect. A rate table is the right design: it is immediate, it is per-request, and it can be attributed to a customer or a feature, which an invoice never can. It is also the only thing that can answer before a request is made, which is what estimating cost before the request depends on. The defect is treating its output as though it were the bill.

Why this stopped being an accounting curiosity

The FinOps Foundation's 2026 survey — 1,192 respondents, more than $83 billion in annual cloud spend between them — found that 98% now manage AI spend, against 63% a year earlier2. FinOps for AI is the report's top forward-looking priority, and AI cost management is the top skill respondents say their teams need to build2.

The three obstacles they name, in order, are visibility into AI costs, allocating those costs to business units, and determining what the spend returned2. Visibility comes first. Not optimisation, not commitment management — knowing what the number is.

Two years ago an AI bill was small enough that being 7% out did not matter to anyone. Now it is a line item that a finance team has opinions about, and "our dashboard says a different thing from your invoice" is a conversation that ends with the dashboard being distrusted rather than fixed.

The seven places an estimate drifts

Source of driftDirectionWhy the table misses it
Prompt cachingBoth ways at onceCache writes cost more than plain input, cache reads cost far less, and the counts arrive in separate fields
Negotiated ratesEstimate too highThe table holds the public list price; your contract does not
Service tiersEstimate too high or absentBatch and priority pricing differ from standard, and at least one tier is missing from a cost endpoint entirely
Rates set by the requestEitherClaude Haiku 5.5 prices a prompt over 100,000 tokens at five times the rate below it3; DeepSeek charges twice its off-peak rate in published peak hours4. A rate held per model cannot follow either
Day boundaries and settlementEither, then cancelsA request at 23:59 UTC lands in different days in the two systems; some charges settle late
Unpriced modelsEstimate too lowA model with no rate contributes zero to the estimate and a real number to the invoice
Traffic the gateway never seesEstimate too lowConsole use, playgrounds, evaluation scripts, another team's key on the same account
The recurring reasons a computed cost and a billed cost disagree.

Two of these deserve more than a row.

Prompt caching is the big one

Caching is where most rate tables are wrong, because it is priced as a multiple of the base input rate rather than as its own number, and because the token counts arrive split across fields that are easy to add up incorrectly.

Anthropic's published multipliers are precise: a cache write costs 1.25× the base input price at a five-minute TTL and 2× at one hour, and a cache read costs 0.1× — except on Claude Opus 5.5 and Sonnet 5.5, where reads are 0.05×, and on Claude Fable 5.1 and Mythos 5.1, where they are 0.025×5. The read multiplier is a property of the model, not of the vendor, so a table that stores one multiplier per vendor is wrong for some of that vendor's models. The usage object reports cache_creation_input_tokens and cache_read_input_tokens separately from input_tokens, and the documentation is explicit that input_tokens counts only the tokens after the last cache breakpoint, so the true total is the sum of all three5.

Now consider a table that models the read discount but not the write premium — a very easy table to write, because the discount is the part everyone markets. Every cached token is priced correctly on the way out and 25% too cheap on the way in. The estimate is low, and it is low specifically on the workloads that cache hardest, which are the large-system-prompt agent workloads that dominate a modern bill. The error is not random; it is concentrated exactly where the money is.

Rates you were given are not rates you were quoted

A negotiated rate is invisible to any default table by construction. So is a committed-use discount, a promotional balance, a regional premium and a tier you were moved onto. Every one of these makes the estimate high, which is the less alarming direction and therefore the one nobody investigates.

What the providers will actually tell you

Both major providers publish organization-level cost reporting, behind a credential that is deliberately not the one your application uses. This is the part most teams do not know exists.

OpenAI Costs APIAnthropic Cost API
Endpoint/v1/organization/costs6/v1/organizations/cost_report7
CredentialAdmin key6Admin key; workspace keys are refused7
Time parametersstart_time, end_time in Unix seconds6starting_at, ending_at as RFC 33397
Bucket widthDaily only on this endpoint6Daily only7
GroupingLine item, project6Workspace, or description, which adds parsed model and inference_geo fields7
Amountamount.value as a number, with amount.currency6Decimal strings in cents7
Known exclusions—Priority Tier costs are not in the cost endpoint7
Paginationnext_page cursor, passed back as page6has_more and next_page7
Cost reporting as documented on 13 October 2026. Both providers also publish finer usage endpoints that report tokens rather than money.

Three details in that table have bitten us and will bite you.

The units differ, and one of them is unusual. OpenAI gives you an amount object whose value is a number in the currency named beside it6. Anthropic gives you decimal strings "in lowest units (cents)"7. Read one as the other and you are out by a factor of a hundred — in a figure whose entire purpose is to be surprising, so the usual instinct that a number looks wrong does not fire. Convert at the edge of each adapter, and write a test that asserts the two conversions do not collapse into one.

Daily is as fine as it gets. Neither cost endpoint will tell you what a request cost. That is not a limitation to work around; it is the reason the two numbers are complementary. The provider knows the total and nothing about your customers. Your gateway knows the customer and is estimating the total. Reconciliation is the join.

There are documented holes. Anthropic states that Priority Tier costs use a different billing model and are not in the cost endpoint7, that playground usage carries a null api_key_id, and that the default workspace reports a null workspace_id7. It also notes that the programmatic endpoints are not currently available on Claude Platform on AWS, that code execution appears in the cost endpoint but not in the usage endpoint, and that Claude Enterprise organizations read their cost through a separate Analytics API7. An account using any of these has a variance that will never close, and a reconciliation that does not say so is lying by omission.

Worth noting, because it settles the question of whether this is an exotic use of the API: Anthropic's own documentation lists "Cost reconciliation: Match internal records with Anthropic billing for finance and accounting teams" as an intended purpose of the endpoint7. The capability is not obscure. The practice is.

What a variance report is, and what it is not

It is not a dashboard tile. A single day's gap is almost always timing — a request served at 23:59 UTC that lands on one side in one system and the other side in the other, a charge that settles hours late, a batch that finalises. Those cancel out across a week and mean nothing individually. Publishing them as a daily percentage produces a number that moves for reasons unrelated to what it measures, which is the fastest way to teach people to ignore it.

What means something is direction. If your estimate is consistently 7% under on one provider for most of a week, that is not scatter averaging out. That is a rate you do not model.

So the useful test has four conditions, and each one excludes a specific false positive:

  1. Enough days. Five out of seven, so a day-boundary effect cannot carry it.
  2. A money floor per day. A day with forty cents of spend can be 80% out for entirely uninteresting reasons, and reporting it buries the account spending four thousand dollars.
  3. All leaning the same way. Ordinary scatter produces days in both directions; an unmodelled rate does not.
  4. Every request in the window priced. An unpriced request makes the estimate low by an unknown amount, so a window containing one has a variance that is partly a coverage gap. "Your rates are wrong" and "we have no rate for this model" are different findings with different fixes.

That fourth condition is the one most likely to be dropped for being inconvenient, and it is the one that keeps the report honest. Report unpriced requests as their own number, next to the variance, always.

A worked example of being wrong

The cache-write premium above is not a hypothetical we chose for the article. It is our own defect.

Our own rate table modelled the cache read discount from the beginning, because it is the part every provider publishes prominently. It did not model the cache write premium. Anthropic folds cache_creation_input_tokens into the prompt total — which it must, because that sum is the published total5 — and our pricing then charged every one of those tokens at the plain input rate. The estimate came out low, by 25% on the affected tokens, on precisely the workloads that cache hardest.

It was found by widening the rate model by hand, not by anything watching. It could have been found in a week by a variance report, because it has exactly the signature described above: consistent, one-directional, concentrated on the days the cached workload ran. Instead it was correct-looking for as long as nobody looked.

We publish this for a specific reason. A vendor writing about cost accuracy is making an implicit claim that its own numbers are right. Ours were not, in a way we can describe and date, and the mechanism that would have caught it is the one this article is about. A cost tool that has never found itself wrong has either been lucky or has not checked.

If you are not going to build this

Most teams should not build a reconciliation pipeline. The monthly version takes half an hour and captures most of the value:

  • Mint an admin key at each provider. It is a different credential class from the one your application uses — OpenAI's is created in organization settings, Anthropic's is an Admin API key (sk-ant-admin01-) or another organization-level admin credential, and workspace keys are refused76.
  • Pull last month's daily costs from the cost endpoint into a spreadsheet.
  • Put your own tool's daily totals beside them.
  • Compute the difference per day and for the month, as a percentage of the provider's figure.
  • Write down the monthly percentage. The single number matters less than having last month's to compare it to.
  • Note anything the comparison cannot cover: Priority Tier, playground use, another team on the same account.

If the percentage is stable, you have learned that your estimate is biased by a known amount, which is worth more than an estimate you believe is exact. If it moves, something changed — a model, a tier, a workload, or a provider's price.

Two cautions. Do not reconcile the current day: a partial day written as a whole one makes the variance look enormous every morning and shrink through the afternoon. And re-read a few days back each time rather than only the newest — Anthropic notes data typically appears within five minutes but that delays can be longer7, and a late-settling figure should correct itself rather than stand.

How INFRO reconciles

INFRO estimates cost on every request, from the organization's own negotiated rate where one has been entered — for that provider, or for the model on any provider — otherwise the vendor's published list rate, and records in price_source which it used. Where a provider reports a request's cost in its own response, that figure is recorded instead and marked provider. A model with no rate is recorded as unpriced rather than as zero.

Separately, and only when an organization connects a read-only billing credential, INFRO reads the provider's own cost API once a day and stores the reported figure per provider per day beside its own estimate for the same UTC day; the current day is left out until it ends. A day counts as reconciled only when both figures are present; a day carrying one and not the other is recorded and is explicitly not a reconciliation, for the same reason an unpriced request is not a variance. The comparison is the product: totals, a per-day table, and a variance expressed as a share of the provider's number.

A gap that holds becomes something you can act on. When the estimate leans the same way by more than 5% on at least five of the last seven days, the organization gets a cost.drift alert. A gap that persists becomes a finding that names one likely cause — a negotiated rate nobody entered, a discount that changed, a vendor price change, a premium the rate table does not model, traffic reaching the same account without passing through INFRO, or unpriced requests — with a confidence and the figures it rests on. A negotiated-rate finding needs the ratio of reported to estimated cost to hold within 5% over at least ten days, and can suggest a rate per model once a model has at least seven days and $20 of reported spend. Applying a suggestion writes a rate for that model on that provider, from that day forward. Findings are readable as GET /v1/rate-findings.

Three properties of that design are deliberate and worth stating plainly.

The billing credential is separate from the inference credential, permanently. The key that serves your requests never reads your billing. The admin-scoped key that reads your cost is granted separately, stored encrypted, and never shown again.

Reconciliation never rewrites a request's recorded cost. Both cost APIs report daily and organization-wide. Attributing a daily total back to individual requests would invent a precision the provider did not give, so the per-request estimate stands as the estimate it is, a suggested rate applies only to requests served after it, and the variance is reported alongside.

A provider with no integration shows no variance rather than a variance of zero. Bedrock, Vertex AI and Azure keep their cost in the surrounding cloud's billing system. Zero would read as agreement, and there is nothing to agree with.

Reconciliation covers OpenAI and Anthropic and is included on the Business plan; below Business the console shows a preview of how much of each provider's estimate used the list rate and how many requests were unpriced. The availability of everything described here is listed below.

Why it sits in the gateway

What distinguishes this from the tools in the next section is not the comparison but where it runs: in the same gateway that routes each request, fails over between your connections, and refuses spend before the provider is called. A rate corrected from a finding is the rate the next budget check uses.

That matters because a budget can only be as right as the estimate it counts. In a test on INFRO's sandbox on 2026-09-25 (code at 1ad89a5, a test connection named echo, a $1 organization cap), 50, 200 and 500 concurrent requests — plain, streaming with client disconnects, with key, project and organization caps together, and with injected upstream failures — held in 12 of 12 runs: the most recorded was $0.9720 against $1, every request was either served and recorded or refused with 402 budget_exceeded, and no reservation was left behind; the test write-up has the scenarios and the method. Read it with its limits. The cap counts INFRO's estimate of provider cost, not the provider's invoice, so a provider that bills above the reserved worst case passes the cap by that excess — which is the gap this article is about. A model with no known price is refused while a blocking cap applies (402 unpriced_model_under_budget) unless the organization allows unpriced traffic. It was a sandbox test with a test connection, not production traffic. And admission serializes under load: p95 latency ran from 1.6 to 4.5 seconds, and streams at 500 concurrent requests had a 42-second p95.

Other tools that do this

INFRO is not the only product that compares an estimate against the bill, and a reader choosing one should know the others. Revenium shows an invoiced figure from the provider's billing data beside its own metered figure and describes them as reconciliation points8. Kenda says it reconciles spend against the actual invoice using read-only keys, names OpenAI, Anthropic, Gemini and Bedrock in its examples, and was running a design-partner programme ahead of general availability on 2026-10-139. LLM SpendGuard is an open-source tool for the OpenAI and Anthropic SDKs that compares a local ledger with the provider's own bill and enforces caps before submission10. What differs is where each sits: INFRO does it inside the gateway that also routes the traffic and enforces budgets, which suits a team that wants those in one place, and does not suit a team that wants none of its traffic to pass through a proxy.

The number worth having

The point of reconciling is not to make the estimate exact. It cannot be exact; it is a different kind of number from the invoice and it is more useful than the invoice for everything except paying it.

The point is to know the size and the direction of the gap, so that when someone asks whether the cost-per-customer figure can be trusted, the answer is a measured percentage and a date rather than a shrug. That percentage belongs in the spend report leadership reads, next to the estimate it qualifies. Any tool will tell you what your AI costs. Ask whichever one you use how far off it is, and how it knows.

From the team that builds it

Where this shows up in INFRO

INFRO computes an estimate on every request and, separately, compares it against the provider's own reported cost. Both numbers are the customer's; INFRO takes no share of either.

  • Usage and cost per request

    Private early access

    Every request records its model, latency, token or unit counts, and estimated provider cost, queryable by project and key.

    Read the documentation for Usage and cost per request
  • Negotiated provider rates

    Private early access

    Enter the rates your contracts actually carry, per model and optionally per provider, so estimated cost uses them before the vendor's list rate. Included from the Team plan.

    Read the documentation for Negotiated provider rates
  • Provider cost reconciliation

    Private early access

    Daily comparison of estimated spend against the cost reported by OpenAI's and Anthropic's own cost APIs, using a separate admin credential, with the likely cause of a persistent gap and a suggested rate you can apply. Included on the Business plan.

    Read the documentation for Provider cost reconciliation
  • Budgets and spend ceilings

    Private early access

    A hard cap per organization, project, member, and key, with alerts at your own thresholds.

    Read the documentation for Budgets and spend ceilings
  • Spend anomaly and drift alerts

    Private early access

    Each scope's usual day is learned from its own history; a day that departs from it, a budget forecast to be exceeded, cost estimates drifting from the provider's own figures, unpriced traffic and failing connections become findings in the console. Routed to email on every plan, and to Slack and signed webhooks from the Startup plan.

    Read the documentation for Spend anomaly and drift alerts

INFRO is in private early access. Provider usage is billed to you by your providers; INFRO charges a software subscription and takes 0% of model spend. See plans.

Sources

Numbered in order of first citation. Each was opened and checked against the claim on the date shown.

  1. 1.Custom costs — AI Gateway (opens in a new tab) — Cloudflare. Accessed Oct 13, 2026.Cited as a plain statement of how gateway cost is computed: custom rates override the default or public model costs, and a cached response always shows zero.
  2. 2.State of FinOps 2026 (opens in a new tab) — FinOps Foundation. Accessed Oct 13, 2026.1,192 respondents representing more than $83 billion in annual cloud spend. The 98% and 63% figures and the three named AI cost obstacles are from this report. A "31% two years ago" figure circulates in secondary summaries but is not on the report site, so it is not used.
  3. 3.Pricing (opens in a new tab) — Anthropic. Accessed Oct 13, 2026.Claude Haiku 5.5's prices for prompts up to and over 100,000 tokens, and fast-mode pricing.
  4. 4.Models and pricing (opens in a new tab) — DeepSeek. Accessed Oct 13, 2026.Peak and off-peak prices and the peak-hour window.
  5. 5.Prompt caching (opens in a new tab) — Anthropic. Accessed Oct 13, 2026.Cache write at 1.25x base input for a five-minute TTL and 2x for an hour, cache reads at 0.1x, 0.05x on Claude Opus 5.5 and Sonnet 5.5, and 0.025x on Claude Fable 5.1 and Mythos 5.1.
  6. 6.How to use the Usage API and Cost API to monitor your OpenAI usage (opens in a new tab) — OpenAI. Accessed Oct 13, 2026.Endpoint paths, the admin key, Unix-second time parameters, the daily-only restriction on the Costs endpoint, grouping by line item and project, and the amount object are described here.
  7. 7.Usage and Cost API (opens in a new tab) — Anthropic. Accessed Oct 13, 2026.Endpoint paths, the admin credential requirement, daily-only cost buckets, the cents-as-decimal-strings format, the Priority Tier exclusion, code execution's absence from the usage endpoint, the Claude Platform on AWS note and the data-freshness note are all stated on this page.
  8. 8.Provider integrations (opens in a new tab) — Revenium. Accessed Oct 13, 2026.Describes an Invoiced versus Metered view built from provider billing data, to be used as reconciliation points.
  9. 9.Kenda (opens in a new tab) — Kenda. Accessed Oct 13, 2026.States that it reconciles spend against the actual invoice, with read-only keys; its examples name OpenAI, Anthropic, Gemini and Bedrock. A design-partner programme ahead of general availability at the access date.
  10. 10.llm-spendguard (opens in a new tab) — LLM SpendGuard (GitHub). Accessed Oct 13, 2026.Open-source (MIT) tool for the OpenAI and Anthropic SDKs that compares a local ledger with the provider's own bill and enforces pre-submit caps.

About this article

Written from the published documentation of OpenAI's and Anthropic's usage and cost APIs, Anthropic's prompt-caching pricing and Cloudflare AI Gateway's custom-costs documentation, each opened on the access date recorded below, and from the pricing, metering and reconciliation implementation of the INFRO gateway, which the authors build. Reviewed on 2026-10-13: every source re-opened, vendor figures re-checked, and every INFRO statement re-checked against the docs, the gateway source and the availability registry. The cache-write defect described under "A worked example of being wrong" is our own, taken from the repository history. Every figure in the variance table is illustrative and labelled as such; no customer data was used.

Last checked against its sources on . The next review is due by . No separate named reviewer is recorded for this article.

How articles are written, sourced and corrected is set out in the editorial standards.

Revision history

  1. Added a seventh source of drift (rates set by prompt length or time of day), the 0.05x cache-read rate on Claude Opus 5.5 and Sonnet 5.5, and two more holes in Anthropic's cost reporting. Corrected OpenAI's cost grouping to line item and project. Rewrote the INFRO section to match what ships now: findings that name a likely cause and can suggest a rate, a cost-drift alert to the organization, and the result of a sandbox test of the budget cap. Updated the status of the other tools that reconcile. Retitled from "Nobody reconciles their AI bill": other tools do reconcile, and the new title says what the article teaches; the address is unchanged.
  2. Named the other tools that compare an estimate against the provider's billed cost, removed a closing line that implied few vendors do, and dropped a 31% figure the FinOps report site does not carry.