[BUG] Bedrock/Vertex/Mantle: thinking.display never reaches the request body; client-side (server honors the field), at least two dropping points incl. the provider gate; follow-up to #67729 and #79052

Status Open
Reported on v2.1.170
Maintainer reply None cached
Activity 3 comments · opened Oct 2, 2026

Preflight Checklist

  • [x] I have searched existing issues and this hasn't been reported yet (all prior reports of this class are closed: #67729 stale, #79052 stale, #71599/#79060/#86959 duplicates)
  • [x] This is a single bug report
  • [x] I am using the latest version of Claude Code

What's Wrong?

On the bedrock, vertex, and mantle providers, thinking.display never
reaches the request body. Thinking blocks arrive signature-only with an empty
thinking field on every model whose server-side default is omitted
(Sonnet 5, Opus 4.7+, Claude 5 family). No client configuration can override
it: the explicit --thinking-display summarized flag parses and is accepted,
showThinkingSummaries: true resolves correctly, and both are then discarded
before the request is built. All three provider APIs accept and honor the
field when sent directly (confirmed in #67729 via AnthropicBedrock SDK and
boto3, and in #79052 via request capture on Vertex).

This is the same defect previously reported as #67729 (Bedrock, 2.1.170) and
#79052 (Vertex, 2.1.215, labeled reproduced and regression). Both were
closed by the stale bot without a fix, with #71599, #79060 and #86959
deduplicated into them. It is still present in 2.1.287.

New information beyond those reports: the root cause, read from the 2.1.287
bundle (minified names are build-specific):

// gate A: updated at some point to include mantle:
function H$(e=Me()){return e==="firstParty"||M$(e)||e==="foundry"||e==="mantle"}
// gate B: never updated; no bedrock, no vertex, no mantle:
function Boe(){let e=Me();return e==="firstParty"||M$(e)||e==="foundry"}
function M$(e=Me()){return e==="anthropicAws"||e==="anthropicGoogleCloud"}

function K4(){return a.CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS||UD()}
function Im(){return Boe()&&!K4()}
function LGn(e){return Im()&&$Sn(e)}          // $Sn = per-model interleaved-thinking check

// thinking-config assembly:
//   zm = Um && LGn(We);  Ih = !zm ? void 0 : r.display
// -> when Boe() is false, `display` is silently dropped from the request

Everything upstream of gate B behaves correctly: the display value resolves
to "summarized" from the flag (Mqo: {display:e, source:"flag"}) or from
showThinkingSummaries (NSn), the model checks pass ($Sn returns true on
these providers for current models), and H$ passes. Attachment then dies at
Im() because Boe() has no bedrock/vertex/mantle arm. One predicate
explains every provider variant reported across the five issues above, and
explains why the fix that closed #77460 (which updated H$) did not resolve
them.

What Should Happen?

thinking.display should be forwarded on providers whose APIs accept it (Bedrock, Vertex and Mantle all do), exactly as the same command does on the
first-party API. The fix appears to be one token per provider in Boe (or
reusing H$ there, if the remaining delta between the two gates is
unintentional).

Error Messages/Logs

No error is emitted; the flag and setting are silently ignored.
Representative measurements on 2.1.287, mantle provider, default model,
prompt chosen to reliably trigger thinking:

  baseline:                       thinking_len=0  sig_len=900
  --thinking-display summarized:  thinking_len=0  sig_len=928
  interactive session with showThinkingSummaries: true: identical
  (thinking blocks present and signed, zero chars of text)

Signature size grows with --effort, so reasoning is happening and being
billed; only the text is omitted, exactly as if display:"omitted" was sent.

Steps to Reproduce

PROMPT="Find all three-digit numbers whose digits sum to 15 and whose first digit is twice the third. Reason step by step."

# (A) Bedrock: prints 0
CLAUDE_CODE_USE_BEDROCK=1 ANTHROPIC_MODEL=<any sonnet-5/opus-4-7+ bedrock profile> \
claude -p "$PROMPT" --output-format stream-json --verbose --max-turns 1 \
  --thinking-display summarized \
| jq -r 'select(.type=="assistant") | .message.content[] | select(.type=="thinking") | (.thinking|length)'

# (B) Same command, first-party: prints a positive length
# (C) CLAUDE_CODE_USE_VERTEX=1: prints 0 (see #79052)
# (D) CLAUDE_CODE_USE_MANTLE=1: prints 0

Claude Model

Not sure / Multiple models (any model whose display default is omitted)

Is this a regression?

Yes for Vertex per #79052 (worked <= 2.1.140); #67729 suggests the Bedrock
path may never have forwarded it.

Claude Code Version

2.1.287 (lineage: 2.1.170 -> 2.1.174 -> 2.1.207 -> 2.1.215 -> 2.1.287 all affected)

Platform

AWS Bedrock / Google Vertex / Mantle

Operating System

Linux (Ubuntu 24.04); prior reports on macOS - not platform-specific

Additional Information

  • Impact: on these providers (the standard enterprise setups), thinking is

billed on every request while being unobservable by any configuration:
no agent observability or tracing of reasoning is possible without
bypassing the CLI for direct API calls.

  • Previous reports of this exact defect were closed by the stale bot while

carrying has repro / reproduced labels (#67729, #79052). Given the
root cause above is now located to a single predicate, requesting this one
be triaged rather than aged out; happy to re-verify a fix on any build.

---

UPDATE (2026-10-02, same day): deeper than the gate; server side confirmed working

After filing, we validated the analysis with local same-length byte patches and by capturing the CLI's outgoing request bodies (ANTHROPIC_BEDROCK_MANTLE_BASE_URL pointed at a local logging forwarder). Corrections and new findings:

  1. Gate B is a defect but not the whole story. With gate B widened to include mantle, and even with display forced to a literal at the located thinking-assembly site (Zc={type:"adaptive",display:...}), the wire body still carries bare {"type":"adaptive"}. A same-length marker rename of the display key at that site never appeared on the wire either, for -p or interactive sessions. So the request builder actually serving live sessions on the mantle path is a different code path that ignores the session display config entirely; we could not locate it by source inspection (every {type:"adaptive",display:X} construction and both thinking rebuild switches in the bundle are accounted for and are not it).
  1. Additional -p defect. --thinking-display summarized resolves into the session config at the entrypoint, but displayExplicit is never set on that path, so the non-interactive downgrade function (which forces display:"omitted" for non-interactive sessions unless the display was explicit) cancels the explicit flag. Interactive sessions resolve display from showThinkingSummaries with no provider gate involved, and still produce bare {"type":"adaptive"} on the wire (captured).
  1. The server honors the field. Hand-signed SigV4 request pairs to the mantle gateway (/anthropic/v1/messages), identical except for the field: control {"type":"adaptive"} returns a thinking block with empty text and a signature; {"type":"adaptive","display":"summarized"} returns summarized thinking text. A local re-signing proxy that injects display into otherwise-unmodified CLI requests restores working thinking summaries end to end through the unmodified CLI (verified: thinking_len=398 on a prompt that previously returned 0). The entire failure is client-side request construction.

Net: on 2.1.287 the bedrock/mantle path has at least two independent dropping points (the provider gate reported above, plus whatever builds the wire body for live sessions), and the -p flag path has the displayExplicit regression. Happy to run any diagnostic build or verbose flag against this setup to help pin the wire-builder.

View original on GitHub ↗

3 Comments

dspiegs · 10 days ago

This is happening to me and its blocking me from upgrading to the 5.x models as they wont accept prompting to explain thinking and this bug means I can't even see the summaries

The-DarkMatter · 3 days ago

This issue needs attention as its pending for a long time and it blocks our proper usage of the models.
#677

igorsf · 2 days ago

Confirming this is still present in 2.1.293 (Agent SDK 0.3.293 native binary) on Bedrock, global.anthropic.claude-opus-5-5, us-west-2.

  • claude -p ... --thinking adaptive --thinking-display summarized --effort max → thinking block is signature-only (0 chars). Same for global.anthropic.claude-opus-4-7.
  • Agent SDK option thinking: { type: "adaptive", display: "summarized" } and showThinkingSummaries: true (programmatic settings) are dropped the same way.
  • Direct bedrock-runtime invoke-model with "thinking": {"type":"adaptive","display":"summarized"} returns summarized thinking for Opus 5.5; with "omitted" it's empty. So Bedrock honors the field.
  • The provider gate matches the one described above; in 2.1.293 it still has no bedrock arm.

Impact: ACP clients built on @agentclientprotocol/claude-agent-acp can't show reasoning for any current Opus model on Bedrock.