Build1 distinct publisher3 min readUpdated
A dev.to writeup documents why cache_read_input_tokens falls to zero mid-run: a cache_control breakpoint walks back at most 20 content blocks, and parallel tool calls clear that in one turn.
The Engineer · Build desk
Compiled by The EngineerSomething wrong?How this is made
A run starts healthy, cache reads climbing, and then a dozen tool calls later the reads drop to zero while cache creation jumps to the full conversation length on every subsequent turn, with the prefix byte-identical and nothing reordered [3]. According to a dev.to post on Claude prompt caching, the cause is that cache lookup is bounded: a `cache_control` breakpoint searches backward through at most 20 content blocks to find an existing entry, and if the previously cached block sits further back than that, the request is treated as cold even though a valid entry exists [1].
Count what one agentic turn actually appends. The assistant message contributes one thinking block, one text block, and N `tool_use` blocks; the user message contributes N `tool_result` blocks [5]. Eight parallel tool calls therefore append 18 blocks in a single round trip, and after two such turns a lone trailing breakpoint is 36 blocks past the last cached point [6]. Eleven parallel calls emit 22 or more blocks and blow the window in one turn, after which the whole prefix is rewritten at the 1.25x write multiplier [2]. There is no error and no warning field, only `cache_read_input_tokens: 0` and a creation charge for the full history [4].
This is why chat products never report the problem. One user turn is one text block and one assistant turn is one text block, so it would take ten round trips to travel 20 blocks, and most implementations mark a breakpoint every turn anyway [7].
The money is the reason to care. The post prices Claude Opus 5 at $5/MTok input, a cache read at about $0.50/MTok, and a five-minute cache write at about $6.25/MTok [15]. That write price is exactly 1.25 times base input, consistent with the stated multiplier [20], and read against write it is a 12.5x per-turn swing [16] on a setting nobody chose.
The prescribed fix is not one marker on the last block but a rotating chain: a stride of roughly 15 blocks, with one of the four available breakpoints spent on the last system block and the other three rotated through the message list [9]. The budget is hard at four per request across tools, system, and messages [8]. Since every breakpoint is both a write point and a read point [10], three markers at a 15-block stride cover about the last 30 blocks of history and keep consecutive markers inside the 20-block window [19]. Placement has constraints: only `text`, `image`, `tool_use`, `tool_result`, and `document` blocks can carry `cache_control`, so thinking blocks must be skipped [17], and you cannot set the field on an SDK response object without round-tripping it through `model_dump()` first [18].
Two related items from the same post. Invalidation is tiered rather than all-or-nothing: `tool_choice` changes, images, and toggling thinking preserve the tools-plus-system cache, while only tool-definition changes and model switches force a full rebuild [12]. Because render order is tools, then system, then messages, a breakpoint on the last system block caches both together [11]. Editing the system prompt mid-run invalidates everything downstream unless you append a `{"role": "system"}` message to `messages[]` instead, which the post says works on Claude Opus 5, Opus 4.8, and Fable 5 but not Sonnet 5 [13].
Watch your metering before you watch anything else. `input_tokens` in the usage block is the uncached remainder only, and total prompt size is `input_tokens + cache_creation + cache_read`, so a dashboard graphing `input_tokens` alone will show a flat line while the cache-write line runs away [14].
Follow any of these and your For You feed starts watching them — no settings page required.
Ranked by verification strength, evidence, and original report placement.
A cache_control breakpoint searches backward through at most 20 content blocks to find an existing cache entry; if the previous request's cached block is more than 20 blocks behind the new breakpoint, the lookup fails and the API treats the request as cold even though a valid entry exists.
One agentic turn with 11 parallel tool calls emits 22 or more content blocks, which blows past the 20-block lookback; the next request finds nothing and rewrites the whole prefix at 1.25x.
Symptom: a run starts with cache_read_input_tokens at 40K and climbing, then twelve tool calls later reads drop to zero and cache_creation_input_tokens jumps to the full conversation length on every turn, with no prompt change, no timestamp, no reordered tool, no model switch, and a byte-identical prefix.
The miss is silent: no error and no warning field, just cache_read_input_tokens: 0 and a cache-creation charge for the full history.
Per agent turn the assistant message appends 1 thinking block + 1 text block + N tool_use blocks, and the user message appends N tool_result blocks.
An agent firing 8 parallel tool calls appends 8 tool_use + 8 tool_result + 2 = 18 blocks in one round trip; after two such turns a single trailing breakpoint is 36 blocks past the last cached point.
Evidence-backed comparisons of source perspectives and observed adoption signals. Read the methodology
Which Builder, Operator, and Investor concerns the observed source mix emphasized—not a truth score.
Evidence, demonstrated adoption, hype gap, incentives, and confidence are assessed independently, each on its own current evidence. How these are measured.
Single self-published account, no primary citation
All claims trace to one dev.to post by one author. The mechanism is described precisely and internally consistently, and it ships working code, which lends some technical credibility. But the load-bearing constants (20-block lookback, 4-breakpoint budget, cacheable block types, per-model system-message support, per-MTok prices) are asserted without any link to vendor documentation, changelog, or reproducible measurement, the symptom narrative has no logs or run counts, and the supplied body is truncated mid-sentence on model switching.
No adoption signal in supplied sources
The cluster contains no release, deployment, usage disclosure, benchmark, or pricing-change event. The post describes one author's technique and a suggested code pattern; nothing indicates whether any team has adopted rolling breakpoints or measured a result. No adoption observations could be recorded without inventing facts.
Confident absolutes ahead of the shown evidence
The framing ('the single most expensive thing about Claude prompt caching', 'chat apps never see this', 'a 12x price swing per turn') is stated as settled fact while resting on one unsourced account, and the arithmetic is slightly loose in the direction of drama (the quoted prices divide to 12.5x, not 12x). The underlying mechanism and fix are plausible and specific rather than vaporous, so the overstatement is one of certainty and generality, not fabricated substance.
Practitioner platform post, no disclosed vendor stake
Observable from the supplied material: this is a self-published post on a developer blogging platform, with no vendor sponsorship, product pitch, or commercial offer attached, and no affiliation disclosed. The visible incentive is the ordinary one of practitioner-audience content on such platforms, which rewards confident, prescriptive framing and a striking cost number; that pressure is consistent with the absolutes and the rounded 12x claim. There is no evidence of an incentive to favor or disfavor Anthropic or any tool.
Low: internally coherent but uncorroborated
Confidence is capped by a single-publisher cluster with zero adoption signal and no primary-source verification of any platform constant. It is not lower because the account is technically detailed, self-consistent, falsifiable against the usage fields it names, and accompanied by an implementation that matches its stated stride and budget rules.
leadership
The AI bill nobody reconciles: cost per finished task, not per million tokens1 distinct publisher
build
Anthropic ships a cache differ, and concedes prompt caching was failing silently1 distinct publisher
build
Claude's system prompt grew ninefold in two years. Version yours like code.1 distinct publisher
leadership
A Government Switched Off Two Frontier Models. Your Board Will Want The Fallback Plan.1 distinct publisher
Distinct publishers with included, body-backed reporting in this cluster.
dev.to
1 article · August 21, 2026