NOTAS DE QUEM CONSTRÓI · #015

Cache de prompt: o TTL de 1 hora pode sair mais caro que não cachear

Um time ativa cache de prompt esperando a conta cair, e ela sobe. A conta exata de quantas vezes você precisa reler o cache para o desconto compensar o ágio da escrita.

Welly5 MIN

Cache de prompt: o TTL de 1 hora pode sair mais caro que não cachear

O bug de caixa que não aparece no dashboard

Um time ativa cache de prompt no agente, espera a conta de API cair no fim do mês, e ela sobe. Não é erro de configuração óbvio nem imaginação. É matemática: a Anthropic cobra a escrita do cache com ágio sobre o preço base de input, e se a sessão não reler aquele cache o suficiente antes de expirar, o ágio nunca se paga. Quem lê a documentação por cima só vê a palavra "desconto" e ativa. Quem faz a conta descobre que a economia depende de quantas vezes o mesmo prefixo é reaproveitado, e isso muda a decisão de qual TTL escolher.

Os números estão na documentação oficial da Anthropic sobre prompt caching. Escrever num cache com validade de 5 minutos custa 1,25 vez o preço base de input. Escrever num cache de 1 hora custa o dobro do preço base. Ler de um cache já escrito, nas duas modalidades, custa 0,1 vez o preço base: um desconto de 90% sobre o input normal. Até aqui parece favorável. O problema aparece quando você calcula quantas leituras são necessárias para o ágio da escrita compensar.

A conta que ninguém faz antes de apertar o botão

Use 1 como referência para o preço de processar o prompt inteiro sem cache, uma vez. Sem cache, N chamadas custam N. Com cache, a primeira chamada paga a escrita e as chamadas seguintes, dentro da janela de validade, pagam a leitura.

Chamadas na janelaSem cacheCache de 5 minCache de 1 hora
11,001,252,00
22,001,352,10
33,001,452,20
55,001,652,40
1010,002,152,90

(Valores por chamada assumindo o mesmo volume de tokens de entrada repetido a cada chamada, sem contar tokens de saída, que são cobrados à parte e não mudam com o cache.)

Repare na terceira coluna. Com cache de 1 hora e apenas duas chamadas dentro da janela, o custo é 2,10 contra 2,00 sem cache nenhum. O time ativou a otimização e pagou mais caro que se tivesse deixado desligada. Só a partir da terceira chamada o cache de 1 hora começa a valer a pena. O de 5 minutos já compensa na segunda chamada, porque o múltiplo de escrita é menor.

Isso inverte a intuição mais comum, que é escolher sempre o TTL mais longo para garantir que o cache esteja lá quando precisar. Quanto mais curta a janela, mais rápido o ágio se paga. O TTL de 1 hora só faz sentido quando dá para garantir pelo menos três leituras antes da expiração, o que é comum em sessões longas de agente com várias chamadas de ferramenta seguidas. Numa chamada isolada de classificação ou extração, que roda uma vez e acaba, o cache de 1 hora é dinheiro jogado fora com a etiqueta de otimização.

Onde o cache quebra sem avisar

Tem um segundo jeito de perder dinheiro com cache que não aparece em nenhuma tabela de preço: colocar conteúdo dinâmico antes do bloco marcado para cache. Se o prompt de sistema muda em qualquer detalhe (um timestamp, um contador de turno, uma lista de ferramentas que cresce) antes do ponto de corte, o cache não dá match e o provedor cobra escrita de novo. Em loop de agente isso vira escrita repetida disfarçada de leitura, porque na sua cabeça você "ativou o cache" e na fatura você nunca saiu da primeira linha da tabela.

A prática que resolve é inverter a ordem do prompt. O que é fixo (system prompt, definição de ferramentas, documentação de referência) vem primeiro e leva o marcador de cache. O que muda a cada turno (a fala do usuário, o resultado da última chamada de ferramenta) vem depois, fora do bloco cacheado.

response = client.messages.create(
    model="claude-sonnet-5",
    system=[
        {
            "type": "text",
            "text": system_prompt_fixo,
            "cache_control": {"type": "ephemeral"},
        }
    ],
    messages=historico_da_conversa,
)

O system_prompt_fixo não muda de chamada para chamada dentro da sessão. O historico_da_conversa muda, e por isso fica fora do bloco marcado. Parece óbvio escrito assim, e mesmo assim é o erro mais comum em agente que cresce rápido: alguém adiciona um campo de contexto dinâmico no topo do prompt para resolver um bug, e ninguém percebe que aquilo matou o cache do resto do time.

O que fazer na segunda de manhã

Abre o agente que já está em produção e mede duas coisas. Primeiro, quantas chamadas em média uma sessão faz dentro da janela de cache escolhida. A resposta da API da Anthropic já devolve os campos cache_creation_input_tokens e cache_read_input_tokens em cada chamada, então dá para somar isso direto dos logs sem instrumentar nada novo. Segundo, se o prompt de sistema realmente fica estático durante essas chamadas ou se alguém colocou algo dinâmico antes do marcador.

Se a média de chamadas por sessão for menor que três e o TTL configurado for de 1 hora, troca para 5 minutos ou desliga o cache: você está pagando ágio sem nunca amortizar. Se o prompt de sistema muda a cada turno, mexe na ordem do prompt antes de mexer no TTL, porque nenhum tempo de expiração salva um cache que nunca dá match.

Cache de prompt não é economia automática. É uma aposta de que o mesmo texto vai ser relido um número mínimo de vezes antes de expirar, e essa aposta tem conta para fazer antes de apertar o botão, não depois de olhar a fatura.

A Overflow desenha agentes de IA com esse tipo de decisão calculada antes de ir para produção, não copiada de tutorial. Mais em overflow.codes/ai.

Fontes

COMPARTILHARLINKEDINXWHATSAPP

// NEWSLETTER

O que a gente aprende, você recebe.

Bastidor de projeto, decisão técnica e o que estamos vendo em IA dentro das empresas. Sem enrolação e sem spam.

// PRÓXIMO PASSO

Tem um problema
parecido?