A API verificou a assinatura de um bloco de raciocínio que você reenviou e ela não foi validada: a assinatura foi truncada, alterada ou reenviada vazia, ou o bloco nunca foi assinado pelo Claude — ou, no Claude Fable 5.1 e no Claude Opus 5.5, algo anterior na conversa mudou. Reenviar o mesmo histórico falha da mesma maneira todas as vezes. Encontre o que quebrou e remova os blocos de raciocínio dessa conversa uma vez, depois continue — você perde o raciocínio anterior do modelo, não a conversa.
O erro
// Through Kunavo: the upstream message as it reaches you, typed as Anthropic
// types a 400; no request_id field, the upstream's own id is appended instead:
{"type":"error","error":{"type":"invalid_request_error","message":"messages.1.content.0: Invalid `signature` in `thinking` block (request id: …)"}}
// (the message path, any masking of it and the appended request id vary by upstream)
// From Anthropic's API directly:
{
"type": "error",
"error": {
"type": "invalid_request_error",
"message": "messages.1.content.0: Invalid `signature` in `thinking` block"
},
"request_id": "req_011C..."
}
// messages.{i}.content.{j}: i = position in messages[], j = block index. Both vary.
// An upstream can mask that path (***.***) and append its own request id, as above.
// Claude Code prints the body after "API Error: 400".
// On Claude Fable 5.1 and Claude Opus 5.5 the message can continue:
// "... The block is bound to a different conversation. Remove the block, or set
// `thinking.block_binding.prefix_mismatch_behavior` to "drop_block"."Causas e soluções em resumo
| Causa | Solução |
|---|---|
| A assinatura foi truncada, esvaziada ou editada antes de ser reenviada | Armazene e reproduza cada bloco exatamente como foi retornado. Deixe o SDK montar os turnos transmitidos para que o signature_delta não seja perdido. |
| O bloco nunca foi assinado pelo Claude | Um modelo que não é Claude por trás de uma URL compatível com Anthropic ou um proxy que grava suas próprias assinaturas. Reenvie esses turnos apenas como texto e tool_use. |
| Você trocou a base URL, a conta ou o login no meio da conversa | O Claude Code 2.1.152+ remove assinaturas obsoletas após uma troca de modelo ou login. No seu próprio código, remova o bloco de raciocínio uma vez se a primeira solicitação após a troca falhar. |
| “O bloco está vinculado a uma conversa diferente” (Fable 5.1, Opus 5.5) | O prompt do sistema, as ferramentas ou uma mensagem anterior mudou. Mantenha o histórico somente com acréscimos ou opte por drop_block (requer um cabeçalho beta). |
| Um proxy ou gateway reescreve o histórico durante o percurso | Essas reescritas contam como suas edições. Reproduza diretamente na API para confirmar ou descartar essa hipótese. |
Leia qual verificação falhou
A redação informa isso. Uma mensagem que termina em “Invalid `signature` in `thinking` block” significa que a própria assinatura não foi validada: a Anthropic lista como causas assinaturas truncadas, alteradas ou devolvidas vazias (https://platform.claude.com/docs/en/build-with-claude/thinking-troubleshooting, em setembro de 2026), e sua página sobre thinking preservado chama isso de uma assinatura adulterada ou impossível de descriptografar que sempre retorna 400. Um caminho mascarado como ***.***.content.0 ou um ID de solicitação anexado por um gateway não muda isso; o que importa é se vem depois uma frase sobre a conversa. No Claude Fable 5.1 e no Claude Opus 5.5, as mesmas palavras podem continuar com “The block is bound to a different conversation” — uma verificação diferente, abordada na última etapa. Uma terceira mensagem, “blocks in the latest assistant message cannot be modified”, significa que o turno mais recente do assistente foi editado, filtrado, reordenado ou reconstruído; texto de thinking editado produz esse erro, não um erro de assinatura. Repetir o mesmo corpo não elimina nenhum deles.
Invalid `signature` in `thinking` block
-> the signature did not verify: truncated, altered, empty, or not Claude's
Invalid `signature` in `thinking` block. The block is bound to a different conversation. ...
-> Fable 5.1 / Opus 5.5: system, tools or an earlier message changed after the block was made
`thinking` or `redacted_thinking` blocks in the latest assistant message cannot be modified
-> the newest assistant turn was edited, filtered, reordered or rebuilt before it was sent backEnvie os turnos do assistente exatamente como foram retornados
Cada bloco de thinking carrega uma assinatura — uma cópia criptografada de todo o raciocínio — e a API a utiliza para verificar se o bloco foi gerado pelo Claude (https://platform.claude.com/docs/en/build-with-claude/thinking#thinking-encryption). Anexe a lista de conteúdo da resposta sem alterações: blocos thinking, redacted_thinking e tool_use, incluindo blocos de thinking cujo texto esteja vazio, que é a exibição padrão nos modelos mais recentes. Durante o streaming, a assinatura chega em um único signature_delta imediatamente antes do fechamento do bloco; portanto, um acumulador feito manualmente que não o capture armazena uma assinatura vazia, e um bloco reenviado com assinatura vazia falha; a recomendação da Anthropic é deixar o SDK montar a mensagem. A ordem das chaves JSON e os espaços em branco não importam — os valores, sim.
import anthropic
client = anthropic.Anthropic(base_url="https://api.kunavo.com", api_key="sk-kn-...")
tools = [{
"name": "get_weather",
"description": "Current weather for a city.",
"input_schema": {
"type": "object",
"properties": {"city": {"type": "string"}},
"required": ["city"],
},
}]
messages = [{"role": "user", "content": "What's the weather in Paris?"}]
with client.messages.stream(
model="claude-sonnet-4-6",
max_tokens=16000,
thinking={"type": "adaptive"},
tools=tools,
messages=messages,
) as stream:
final = stream.get_final_message() # signature_delta already applied
# Append the content list untouched: thinking, redacted_thinking, tool_use.
messages.append({"role": "assistant", "content": final.content})
# Not this: a store that keeps the text but not the signature replays
# {"type": "thinking", "thinking": "...", "signature": ""} -> this 400.Mantenha o thinking de outros backends fora do histórico do Claude
Segundo a documentação da Anthropic, alternar entre modelos Claude na própria API não deve causar isso: ela pede que você continue enviando os blocos ao alternar, descarta os que o novo modelo não consegue ler sem gerar erro e documenta as assinaturas como portáteis entre a Claude API, o Amazon Bedrock e o Google Cloud (https://platform.claude.com/docs/en/build-with-claude/thinking, em setembro de 2026). O que ela não consegue verificar é um bloco que o Claude nunca assinou. Os relatos públicos envolvem históricos que passaram por outro backend: uma sessão do Claude Code que executou em um backend GLM e depois voltou à Anthropic (github.com/anthropics/claude-code/issues/21726), turnos do Gemini que um proxy apresentou como blocos de thinking do Claude com assinaturas próprias (github.com/router-for-me/CLIProxyAPI/issues/1584), e uma sessão do Claude Code que mudou para outra chave no meio da sessão e voltou (github.com/lbjlaq/Antigravity-Manager/issues/388). Para turnos produzidos por um modelo que não seja Claude, a recomendação da Anthropic é reenviar a saída desse modelo apenas como conteúdo de texto e tool_use.
def as_foreign_turn(content: list[dict]) -> list[dict]:
"""A turn a non-Claude model produced: keep what it said and did,
never its thinking blocks, which Claude cannot verify."""
return [b for b in content if b["type"] in ("text", "tool_use")]Recupere uma conversa que já apresenta falhas
Remova uma vez os blocos thinking e redacted_thinking do histórico armazenado — remover todos é o mais simples; para a variante “bound to a different conversation”, o mínimo declarado pela Anthropic é o bloco indicado e todos os blocos posteriores — mantenha todos os outros blocos no lugar, salve esse histórico e continue. A Anthropic apresenta isso como recuperação para uma sessão salva que não pode mais ser reproduzida (https://platform.claude.com/docs/en/build-with-claude/preserved-thinking#faq); quando uma assinatura não é validada, a única outra saída é reproduzir o bloco exatamente como foi retornado, se você ainda o tiver. O Claude Code remove sozinho o thinking anterior quando a API rejeita uma assinatura. Depois de remover os blocos e prosseguir, não os coloque de volta: no Fable 5.1, um bloco removido e recolocado invalida o thinking produzido enquanto ele esteve ausente. O modelo responde sem o raciocínio anterior, e o novo thinking é válido a partir daí. No Claude Code, a versão 2.1.152 (27 de maio de 2026, https://code.claude.com/docs/en/changelog) remove assinaturas obsoletas após uma troca de modelo ou login, e seu guia de gateway informa que ele repete uma rejeição de assinatura sem os blocos de thinking anteriores — mas essa repetição procura o texto de erro do upstream, e um gateway que envolve os erros em seu próprio envelope pode quebrá-la (https://code.claude.com/docs/en/llm-gateway-protocol#automatic-retry-and-error-forwarding).
THINKING = {"thinking", "redacted_thinking"}
def block_type(b) -> str:
return b["type"] if isinstance(b, dict) else b.type # dicts or SDK objects
def strip_thinking(messages: list[dict]) -> list[dict]:
"""One-time recovery: drop every thinking block, keep everything else."""
out = []
for m in messages:
content = m["content"]
if m["role"] == "assistant" and isinstance(content, list):
kept = [b for b in content if block_type(b) not in THINKING]
content = kept or [{"type": "text", "text": "(no visible reply)"}] # keep the turn non-empty
out.append({**m, "content": content})
return out
messages = strip_thinking(messages) # save this version; never re-add the blocksNo Fable 5.1, mantenha o prefixo fixo — ou opte por drop_block
“Bound to a different conversation” é a verificação de thinking preservado: no Claude Fable 5.1 e no Claude Opus 5.5, um bloco reproduzido só é válido enquanto o prompt do sistema, as ferramentas e todas as mensagens anteriores permanecerem inalterados. A Anthropic aplica isso por padrão a contas criadas em ou após 31 de agosto de 2026 (https://platform.claude.com/docs/en/build-with-claude/preserved-thinking#enforcement); atrás de um gateway, essa conta não é sua, portanto, presuma que a regra está ativa. Mantenha o sistema e as ferramentas fixos durante a sessão e anexe em vez de editar. Para manter as solicitações funcionando enquanto você identifica a edição, envie o cabeçalho beta thinking-binding-controls-2026-08-01 com prefix_mismatch_behavior definido como drop_block; sem esse cabeçalho, o próprio campo é rejeitado com “block_binding: Extra inputs are not permitted” (https://platform.claude.com/docs/en/api/errors).
# Anthropic's API directly. The field needs the beta header; Kunavo forwards it (see below).
curl https://api.anthropic.com/v1/messages \
-H "x-api-key: $ANTHROPIC_API_KEY" \
-H "anthropic-version: 2023-06-01" \
-H "anthropic-beta: thinking-binding-controls-2026-08-01" \
-H "content-type: application/json" \
-d '{
"model": "claude-fable-5-1",
"max_tokens": 16000,
"thinking": {
"type": "adaptive",
"block_binding": {"prefix_mismatch_behavior": "drop_block"}
},
"messages": [{"role": "user", "content": "..."}]
}'Se você estiver chamando pela Kunavo
O Kunavo encaminha os blocos thinking e redacted_thinking por /v1/messages exatamente como foram enviados, incluindo assinatura e dados — as únicas alterações na solicitação são o ID do modelo e, nos modelos que os rejeitam, a remoção de temperature, top_p e top_k — e retorna o corpo da resposta, com ou sem streaming, exatamente como o upstream o enviou. Em setembro de 2026, cada modelo Claude é servido por um único canal upstream, sem fallback; portanto, o roteamento do Kunavo não move uma conversa entre provedores, e um 400 nunca é repetido em outro local. Não testamos mover uma conversa entre a Anthropic diretamente e o Kunavo, então espere que a primeira solicitação após essa troca precise ter o thinking removido. Desde 24 de setembro de 2026, o Kunavo encaminha o beta thinking-binding-controls-2026-08-01; em um teste realizado naquele dia, o canal que servia o Claude aceitou block_binding no Claude Fable 5.1 com ou sem o cabeçalho, e não observamos a remoção de um bloco. A rejeição chega como HTTP 400 do tipo invalid_request_error, sem um campo request_id, contendo o texto da mensagem do upstream — que pode mascarar o caminho messages.N e terminar com o próprio request id do upstream — portanto, faça a correspondência pelo status e pelas palavras “Invalid `signature` in `thinking` block”. A remoção e repetição automáticas do Claude Code usam essa redação como chave: o Claude Code 2.1.280, apontado para um servidor de teste que respondia nesse envelope, removeu os blocos de thinking e repetiu a solicitação. Não provocamos o erro pelo próprio Kunavo; portanto, se uma sessão continuar falhando em todos os turnos, inicie uma nova. Solicitações com falha não são cobradas. O que o endpoint nativo encaminha sem alterações está listado na referência da Messages API.
Perguntas frequentes
O que significa “Invalid `signature` in `thinking` block”?
A API não conseguiu verificar um bloco de thinking que você reenviou. Cada bloco de thinking carrega uma assinatura — uma cópia criptografada do raciocínio do Claude — e a verificação falha quando essa assinatura foi truncada, alterada ou reenviada vazia, ou quando o bloco nunca foi assinado pelo Claude. É um 400, não um erro transitório: a mesma solicitação falha todas as vezes.
As assinaturas dos blocos de thinking expiram?
A documentação da Anthropic não menciona expiração. No rastreador do anthropic-sdk-python (issue #1598, agosto de 2026), uma resposta de uma conta que o GitHub identifica como colaboradora afirma que não expiram e que a verificação falha quando o bloco que chega à API difere do que foi retornado — é um comentário em issue, não documentação. Se uma sessão salva que funcionava antes agora falha, procure o que pode ter alterado os blocos armazenados ou o caminho que percorreram: sua camada de armazenamento, um proxy ou uma troca de backend.
Posso simplesmente excluir os blocos de thinking e continuar?
Sim. A Anthropic apresenta isso como recuperação para uma sessão salva que não pode ser reproduzida, e o Claude Code remove sozinho o thinking anterior quando uma assinatura é rejeitada. Remova os blocos thinking e redacted_thinking — remover todos é o mais simples — mantenha os outros blocos e repita uma vez. O modelo perde o raciocínio anterior, não a conversa; fora do uso de ferramentas, a documentação da Anthropic permite deixar de fora o thinking de turnos anteriores.
Por que isso acontece depois de trocar de modelo ou provedor?
A documentação da Anthropic afirma que uma troca entre modelos Claude em sua API descarta, sem erro, os blocos que o novo modelo não consegue ler, e que as assinaturas funcionam entre a Claude API, o Amazon Bedrock e o Google Cloud. Ainda assim, o Claude Code precisou corrigir sessões presas em assinaturas obsoletas após uma troca de modelo ou login (2.1.152), e os relatos públicos envolvem históricos que passaram por algo que o Claude não consegue verificar — um modelo que não é Claude atrás da mesma base URL, um proxy que escreve suas próprias assinaturas ou um cliente que as perdeu. Remova os blocos de thinking uma vez após a troca.
O Claude Code corrige isso automaticamente?
As versões recentes tentam fazer isso. Desde a 2.1.152, ele remove assinaturas obsoletas após uma troca de modelo ou login e repete uma rejeição de assinatura sem os blocos de thinking anteriores. Essa repetição procura o texto de erro do upstream, e o guia de gateway da Anthropic informa que um gateway que envolve os erros em seu próprio envelope pode quebrá-la. Execute claude update primeiro; se uma sessão ainda falhar em todos os turnos, inicie uma nova sessão.
Guias relacionados
- Claude API 400 “tool_use ids foram encontrados sem blocos tool_result” — a regra de ordenação
- Claude Code Router — encaminhe o Claude Code para qualquer modelo ou ignore o roteador completamente
- Erros de streaming de LLM — cortes de SSE, streams travados e uso ausente
- Claude Code “context_management: Extra inputs are not permitted” — o cabeçalho beta que não chegou
Mais detalhes sobre o significado dos erros estão em referência de erros; obter uma chave leva um minuto por meio de cadastro e da guia de autenticação.