Skip to main content
O ChatCLI implementa um sistema completo de gerenciamento de resultados de ferramentas que garante integridade, controla o tamanho do contexto e compacta resultados antigos progressivamente. Isso e essencial para sessões longas de agente onde dezenas de tool calls podem saturar a janela de contexto.

Pareamento de Tool Results

Toda tool_use (chamada de ferramenta pelo modelo) deve ter um tool_result correspondente no histórico de conversacao. Quando essa correspondencia quebra — por interrupcao, timeout ou erro silencioso — a API rejeita o histórico. O sistema EnsureToolResultPairing valida e repara automaticamente:

Resultados Sinteticos

Quando uma tool_use não tem resultado correspondente, o ChatCLI injeta:
A mensagem instrui o modelo a não repetir a tool call falha, evitando loops infinitos de retentativa.

Validação em 3 Fases

1

Coleta de IDs

Percorre todo o histórico coletando IDs de tool_use (de mensagens assistant) e IDs de tool_result (de mensagens tool).
2

Detecção de Desalinhamentos

Compara os dois conjuntos de IDs. Tool uses sem resultado sao “missing”. Tool results sem uso sao “orphans”. IDs duplicados sao marcados para dedup.
3

Reconstrucao do Histórico

Reconstroi o histórico: remove orphans, faz dedup de tool_use IDs e injeta resultados sinteticos após mensagens assistant com tool_uses sem resultado.

Orcamento de Resultados (Budget Enforcement)

Resultados de ferramentas como leitura de arquivos grandes ou saida de comandos podem consumir rapidamente a janela de contexto. O sistema de orcamento limita o tamanho agregado em três niveis:

Per-tool truncation (capability)

Plugins que implementam plugins.TruncationAware declaram seu próprio cap — útil quando o tool tem necessidade de contexto fora do padrão: A truncação preserva o shape historic head/tail (preview 5000 chars + suffix 1000 chars + marker [TRUNCATED N chars omitted, M kept]).

Como Funciona o Enforcement

O orcamento e aplicado em duas passadas:
Cada resultado individual e verificado contra DefaultPerResultMaxChars (20KB). Se exceder, o conteúdo completo e salvo em disco e substituido por um preview:

Persistência em Disco

Resultados truncados são salvos em arquivos temporários dentro do Workspace de Sessão, em vez do antigo diretório global /tmp/chatcli-tool-results/:
A mudança para o diretório por sessão tem dois efeitos importantes:
  1. Isolamento entre sessões. Múltiplas instâncias de chatcli rodando em paralelo no mesmo host não compartilham mais o pool de overflow.
  2. Leitura sob demanda pelo agente. O scratch dir está na allowlist de leitura do agente, então quando o modelo encontra a marca [full output saved to ...] no preview, ele consegue abrir o arquivo com read_file:
Antes desta versão, o caminho era um beco sem saída — o read tool bloqueava por estar fora do workspace boundary. O orçamento “salvava o output” mas o agente não tinha como acessá-lo.
Os arquivos são limpos automaticamente quando a sessão termina (ChatCLI.cleanup), respeitando CHATCLI_AGENT_KEEP_TMPDIR=true para depuração. Não é mais necessária uma limpeza global periódica.

Preview: Head + Tail

O preview mantem o inicio e o final do resultado para maximizar utilidade:

Microcompactacao Progressiva

A microcompactacao reduz progressivamente o tamanho de resultados antigos de ferramentas conforme a conversa avanca, sem perder informação crítica: Com a camada de compressão ativa, os dois níveis são sem perda: o resultado original é arquivado no store CCR antes do corte e o preview/summary carrega um marcador <<ccr:KEY>> (preservado entre níveis) que o modelo expande com @recall.

Detecção de Tipo de Conteúdo

O resumo identifica automaticamente o tipo do conteúdo para contexto:

Configuração da Microcompactacao

Apenas resultados com mais de 3.000 chars sao compactados. Resultados pequenos sao sempre preservados. Resultados de ferramentas de escrita e execução sao preservados por conterem informações críticas de erro.

Agendamento Consciente do Cache

Toda reescrita de uma mensagem antiga invalida o prefixo cacheado do provider daquela mensagem em diante: na Anthropic e no Bedrock a cauda inteira é cobrada de novo como escrita de cache (1,25x ou 2x o preço de input); na OpenAI, Gemini, xAI, Kimi e nos demais providers com cache de prompt ela é cobrada a preço cheio em vez do desconto de cache. Raspar algumas centenas de tokens de um resultado que já vem do cache não paga essa conta. Por isso microcompactação, dedup de leituras repetidas e skill aging são agendados contra o cache, em todos os providers:
  • Enquanto o cache de prefixo está quente e o histórico está abaixo de CHATCLI_HISTORY_REWRITE_PRESSURE do budget de compactação, os passes esperam. Os resultados antigos seguem como leituras baratas de cache.
  • Quando o histórico atinge essa fração, os passes rodam: encolher agora é o que mantém longe a compactação com sumarização, muito mais cara.
  • Sem prefixo quente a proteger (provider que não reporta cache, cache expirado, primeiro request) os passes rodam a cada turno como sempre rodaram.
O mesmo gate vale para workers de squad, taskgraph e delegate. CHATCLI_HISTORY_REWRITE_PRESSURE=0 restaura o comportamento só por idade.

Fluxo Completo

O gerenciamento de resultados e aplicado nesta ordem durante o loop do agente:

Configuração Completa


Próximos Passos

Workspace de Sessão

Onde os arquivos de overflow vivem e como o agente os lê.

Subagent Delegation

Estratégia complementar para evitar saturar o contexto com dados brutos.

Recuperação de Contexto

O que acontece quando mesmo com orçamento o contexto transborda.

Cost Tracking

Monitore o consumo de tokens incluindo tool results.