DEV Community

Cover image for Why did Claude Code make 13 API calls for my 5 messages?
Sivaram
Sivaram

Posted on Originally published at draining-defaults.sivaramp.com

Why did Claude Code make 13 API calls for my 5 messages?

So I did something a bit paranoid this weekend. I put a traffic tap between Claude Code and the Anthropic API and captured everything it sent.

I typed 5 messages. Normal stuff: a hello, a settings question, two harmless shell commands, and a look at the result.

Claude Code made 13 API calls.

Thirteen! For five messages! I had to know where the other eight went.

The headline numbers: 13 API requests, 2.6x amplification, 544,266 tokens, 98.6% warm cache hit, 38.6% hidden thinking, ~$1.20 list-price equivalent
The headline numbers from one tiny session. Look at that token total!

What the 13 calls actually were

Once I labeled every request in the capture, the picture got really interesting:

Turn What it actually was
1 A 1-token "quota" probe (got rejected with a 429!)
2 Hidden call to generate the session title
3 My greeting, finally
4 Response after a local command
5 Hidden call to generate a prompt suggestion for me
6 Hidden "welcome back" recap because I tabbed away
7 Proposing my first shell command
8 A separate security model checking that command
9 Reading the result and answering
10 Answering my settings question
11 Proposing the second shell command
12 The security model, again
13 Reading the result and answering

Only 7 of these were the actual conversation. The other 6 were probes and background work I never asked for and never saw.

Waterfall of all 13 requests colored by call type: blue main loop, orange security classifier, green hidden auxiliary calls, yellow quota probe
Every bar is one API request. Only the blue ones are the conversation I actually saw in my terminal.

That's a 2.6x request amplification. Your coding agent is not a chat window. It's a small orchestration system, and the chat is just the part they show you.

The part that surprised me most: two cache universes

I went in expecting to find broken caching. I found the opposite!

Claude Code runs two completely independent prompt-cache chains:

  • The main conversation: ~50-53k cached tokens, and every warm request read exactly the frontier the previous one created. 98.6% warm hit rate.
  • The auto-mode security classifier: its own separate ~40k token universe on a different model. 99.7% warm hit rate.

Line chart showing two separate cache chains: the main conversation climbing from 42k to 53k tokens, and the classifier flat at 40k
Two chains that never touch. The classifier lives in its own 40k-token world.

The caching is honestly excellent. The cost isn't coming from cache thrash. It's coming from the architecture: maintaining two large prompt universes and making hidden calls between your visible ones.

Total accounting for this tiny session: 544,266 tokens. 78% of that was cache reads (the cheap kind), but the expensive part was the two cold starts writing ~100k tokens of cache. List-price equivalent: about $1.20. For five messages!

Stacked columns of token usage per turn: blue cache reads dominate, with two orange cache-creation cold-start spikes at turns 3 and 8
Where the 544k tokens went. See those two orange cold starts? That's where the money is.

(To be fair: that's a comparison number, not my actual bill. Subscriptions change the math completely.)

Auto mode taxes every shell command

This is the one that actually changed my settings.

Every time Claude Code wanted to run a shell command, a second model got called first to classify it for safety. My command was cat-ing my own settings files. Severity score: 2 out of 100. Completely harmless. Still cost a model round trip.

For one shell action, the timing looked like this:

  • Main model picks the tool: 2.67s
  • Security model classifies it: 1.69s
  • Main model reads the result: 5.70s

Timeline of one shell action: 2.67s tool selection, 1.69s security classification, 5.70s consuming the result, 10.05s total model time
10 seconds of model time for one cat command. The orange slice is the security tax.

That's ~1.7 seconds of pure classifier overhead, per command. In a tool-heavy session with dozens of commands? It adds up fast.

Also: you're paying for thinking you never see

On the text-answer turns, 38.6% of the output tokens were redacted thinking. Billed, counted, invisible. One turn was 70% hidden!

I'm not even mad about this one, the reasoning probably makes the answers better. But it's another thing nobody tells you when you're staring at your token usage wondering where it all went.

The settings I changed

Here's the practical part. Before a long, supervised agentic run, I now flip these in ~/.claude/settings.json:

{
  "promptSuggestionEnabled": false,
  "awaySummaryEnabled": false,
  "disableAutoMode": "disable",
  "permissions": {
    "defaultMode": "acceptEdits"
  },
  "outputStyle": "Concise"
}
Enter fullscreen mode Exit fullscreen mode

Three gotchas that cost me time:

  1. disableAutoMode takes the string "disable", not a boolean. Yes really.
  2. Output style is read once per conversation, so /clear or restart after changing it.
  3. Don't reach for bypassPermissions to "save the classifier call". That removes the approval checks, not just the overhead. (tbh on throwaway repos I start in yolo mode anyway, but anywhere real, acceptEdits + scoped allow rules is the move.)

What I can and can't prove

Being honest here, because one observational trace is not a benchmark:

Solid: the 13 requests, the hidden calls, the two cache chains, the per-command classifier, the redacted thinking share. It's all in the capture.

The full per-request log: every turn with durations and token counts, cold starts highlighted in orange, the slowest request in blue
The receipts. Orange cells are the two expensive cold starts, blue is the slowest request.

Not proven yet: my actual billed amount, and the exact savings from each setting. That needs a controlled before/after run with the same prompts. It's on my list!

The takeaway

When people argue about coding-agent efficiency, they count chat messages. Wrong unit! Count the full system of model calls behind them.

I turned the whole capture into an interactive report with every chart, the full per-request log, and the copyable config:

draining-defaults.sivaramp.com

The traffic was captured with claude-tap, which made all of this observability possible. And before anyone worries: everything was sanitized before analysis, no account metadata, no paths, no identifiers.

Have you ever traced what your coding agent actually sends? I'd genuinely love to compare numbers with other tools. Tell me in the comments!

Top comments (0)