12k
All articles

LLM Harnesses: Por Que o Wrapper Importa Mais do Que o Modelo

Não só o modelo importa: harnesses de LLM moldam o sucesso do agente. Orquestração, ferramentas, contexto e verificação.

OpenReplay Team
OpenReplay Team
LLM Harnesses: Por Que o Wrapper Importa Mais do Que o Modelo

O harness é todo o código, configuração e lógica de execução que não é o modelo em si — o loop de orquestração, ferramentas, memória, gerenciamento de contexto, estado, tratamento de erros, guardrails e verificações que, em conjunto, determinam se um agente terá sucesso ou falhará. Se você já publicou uma funcionalidade com LLM usando o SDK da OpenAI ou da Anthropic e observou o sistema entrar em loop, alucinar chamadas de ferramentas ou esquecer o que o usuário disse três turnos atrás, você já atingiu os limites de um harness superficial — e, na maioria das vezes, o modelo não era o problema.

Este artigo oferece um modelo mental preciso para o harness, evidências de que ele gera mais variância nos resultados do que a escolha do modelo, um harness em JS/TS executável que você pode ler do início ao fim, e quatro decisões que uma equipe de frontend realmente controla ao publicar uma funcionalidade de IA em um produto.

Principais Conclusões

  • O harness é todo o código, configuração e lógica de execução que não é o modelo em si; Vivek Trivedy, da LangChain, resume isso como: “se você não é o modelo, você é o harness.”
  • A equipe v0 da Vercel removeu 80% das ferramentas do agente e observou a taxa de sucesso subir de 80% para 100%, o uso médio de tokens cair 37% e uma consulta no pior caso passar de 724 segundos para 141 — sem alterar o modelo.
  • No leaderboard CORE-Bench Hard do Princeton HAL, o Claude Opus 4.5 obtém 42,22% com o CORE-Agent e 77,78% com o Claude Code — uma diferença de 35,56 pontos impulsionada pelo scaffold, no mesmo modelo.
  • O debate harness vs. modelo não está encerrado: o SWE-Atlas da Scale AI mostra que os efeitos do scaffold variam conforme o modelo, enquanto a METR constatou que o Claude Code e o Codex não foram estatisticamente superiores aos seus próprios scaffolds padrão em uma avaliação de horizonte temporal.
  • Todo harness precisa de pelo menos uma verificação determinística — um teste, um validador de schema, uma regex — antes de retornar o resultado ao usuário.

O que é um agent harness?

Um agent harness é o sistema de software completo que envolve uma chamada a um LLM: o loop de orquestração que decide quando chamar o modelo, as ferramentas que o modelo pode invocar, a memória e o contexto que ele enxerga, o estado que carrega entre os turnos, e os guardrails e verificações que controlam seu output. A fórmula canônica vem de Vivek Trivedy, da LangChain: “se você não é o modelo, você é o harness.” O modelo produz tokens; o harness é tudo o que transforma esses tokens em uma funcionalidade confiável.

O modelo mental mais claro para essa relação vem do ensaio de 2023 de Beren Millidge, que enquadra sistemas LLM com scaffold como computadores em linguagem natural: o LLM corresponde à CPU, o prompt e a janela de contexto correspondem à RAM (rápida, porém limitada), e a memória externa, como um banco de dados vetorial, corresponde a um armazenamento semelhante a um disco. As ferramentas funcionam como drivers de dispositivo que acessam o mundo externo, e o harness é o sistema operacional que coordena tudo isso. Uma CPU sem sistema operacional não computa nada útil. O modelo é necessário, mas não suficiente.

A terminologia nessa área é extensa, então vale fixar os conceitos de uma vez. O model é o LLM — pesos e uma API. O harness (às vezes chamado de scaffold) é o código ao redor. O agente é o comportamento emergente: uma entidade orientada a objetivos, que usa ferramentas e se autocorrige, com a qual o usuário interage. O Curso de Agentes da Hugging Face define um agente como um sistema que utiliza um modelo de IA para interagir com seu ambiente e alcançar um objetivo definido pelo usuário. Quando alguém diz “construí um agente”, na prática construiu um harness e o apontou para um modelo. O próprio anúncio do Claude Agent SDK pela Anthropic descreve o Claude Code SDK como “o agent harness que alimenta o Claude Code.”

Por que o wrapper importa mais do que o modelo?

O wrapper importa mais do que o modelo porque o mesmo modelo, por trás de um harness diferente, produz resultados radicalmente distintos — e essas diferenças são grandes, recorrentes e mensuradas em benchmarks públicos. O dado mais contundente: a equipe v0 da Vercel removeu 80% das ferramentas do agente e observou a taxa de sucesso subir de 80% para 100%, o uso médio de tokens cair 37% e uma consulta no pior caso passar de 724 segundos para 141 — sem alterar o modelo. A correção foi inteiramente no harness: menos ferramentas, com escopo melhor definido.

Dois outros resultados apontam na mesma direção. A LangChain relatou ter movido seu agente de codificação de fora do top 30 para o top 5 no Terminal-Bench 2.0 alterando apenas o harness ao redor de um modelo inalterado, conforme seu próprio relato. E no leaderboard CORE-Bench Hard do Princeton HAL, o Claude Opus 4.5 obtém 42,22% com o scaffold CORE-Agent e 77,78% com o Claude Code — uma diferença de 35,56 pontos no mesmo modelo, com o leaderboard também reportando 95,5% na validação manual da execução com Claude Code.

EstudoModelo alterado?Harness alterado?AntesDepois
Vercel v0NãoSim (−80% ferramentas)80% de sucesso100% de sucesso, −37% tokens
LangChain / Terminal-Bench 2.0NãoSimFora do Top 30Top 5
Princeton CORE-Bench HardNão (Opus 4.5)Sim (scaffold)42,22%77,78%

O debate não está encerrado, e simplificá-lo em excesso compromete a credibilidade. O SWE-Atlas da Scale AI compara scaffolds de agentes de codificação proprietários com o mini-SWE-agent minimalista e mostra que os efeitos do scaffold variam conforme o modelo, com scaffolds nativos produzindo melhorias notáveis em relação à linha de base mínima. Por outro lado, a METR constatou que o Claude Code e o Codex não foram estatisticamente superiores aos seus próprios scaffolds padrão em uma avaliação de horizonte temporal. Ambos os efeitos são reais; qual deles predomina depende do regime de tarefas. A leitura honesta, como a MongoDB coloca, é que “o LLM é a menor parte” — mas os ganhos do harness não são ilimitados, e um modelo robusto em uma tarefa simples ainda impõe um teto ao que o scaffolding pode recuperar.

Quais são os componentes de um LLM harness?

Um harness de produção se decompõe em oito componentes, cada um representando um ponto onde um wrapper superficial pode falhar: loop de orquestração, ferramentas, memória, gerenciamento de contexto, construção de prompt, estado, tratamento de erros e guardrails com loops de verificação.

Loop de orquestração. O loop implementa o ciclo Pensamento–Ação–Observação (o padrão ReAct): chama o modelo, verifica se ele solicitou uma ferramenta, executa a ferramenta, alimenta o resultado de volta e repete até que o modelo responda ou um guardrail seja acionado. Como a análise de engenharia reversa do Claude Code feita por Vikash Rungta descreve, o runtime é um “loop burro” onde toda a inteligência reside no modelo e o harness apenas gerencia os turnos. Mecanicamente, é um loop while com um limite de turnos.

Ferramentas. As ferramentas são as mãos do agente — funções expostas ao modelo como schemas (nome, descrição, tipos de parâmetros). A camada de ferramentas cuida do registro, da validação de argumentos, da execução e da formatação dos resultados de volta em observações legíveis pelo modelo. Uma ferramenta search_docs em um widget de ajuda é uma ferramenta; o mesmo vale para get_order_status.

Memória. A memória de curto prazo é a conversa atual; a memória de longo prazo persiste entre sessões. Em um widget de chat, a memória de curto prazo é o array de mensagens que você reproduz a cada turno; a memória de longo prazo pode ser um resumo por usuário que você carrega no início da sessão.

Gerenciamento de contexto. O recurso escasso é a janela de contexto, e o modo de falha é o context rot — a qualidade se degrada quando a janela se enche de tokens de baixo valor. De acordo com as orientações de context engineering da Anthropic, o objetivo é o menor conjunto de tokens de alto valor. As estratégias incluem: compactação (resumir turnos antigos) e recuperação just-in-time (buscar sob demanda em vez de pré-carregar).

Construção de prompt. O harness monta o input de forma hierárquica: system prompt, definições de ferramentas, memória, histórico de conversa e mensagem atual. A ordem importa; contextos importantes devem estar no início e no final da janela.

Estado. O estado é o que sobrevive entre turnos e falhas — a posição do agente em uma tarefa de múltiplos passos, outputs intermediários e checkpoints. Um widget de chat que “esquece” uma restrição declarada anteriormente pelo usuário tem um problema de estado, não um problema de modelo.

Tratamento de erros. Uma tarefa de 10 passos com 99% de sucesso por passo tem apenas ~90% de sucesso de ponta a ponta, porque os erros se acumulam. O padrão-chave: retornar um erro de ferramenta ao modelo como uma observação para que ele possa se autocorrigir, em vez de lançar uma exceção e encerrar a execução.

Guardrails e loops de verificação. Guardrails restringem o que o agente pode fazer; loops de verificação checam o que ele produziu. O artigo de harness engineering de Martin Fowler / Birgitta Böckeler enquadra a verificação como guides (feedforward — orientar antes de agir) e sensors (feedback — observar e se autocorrigir), divididos em controles computacionais (determinísticos: testes, linters) e inferenciais (LLM como juiz).

Como construir um agent harness em JavaScript?

Um harness mínimo, porém completo, é um loop ReAct com um limite de turnos, uma ferramenta bem delimitada, um handler de erro-como-observação e uma verificação determinística. O exemplo abaixo usa o SDK da Anthropic e o Zod para validação de schema. A verificação determinística é a parte que a maioria dos wrappers superficiais omite — sem ela, o agente não tem como saber que está errado.

import Anthropic from "@anthropic-ai/sdk";
import { z } from "zod";

const client = new Anthropic();

// Uma ferramenta, com escopo bem delimitado. Menos ferramentas = menos chamadas espúrias.
const tools: Anthropic.Tool[] = [
  {
    name: "get_order_status",
    description: "Look up the status of an order by its numeric ID.",
    input_schema: {
      type: "object",
      properties: { orderId: { type: "number" } },
      required: ["orderId"],
    },
  },
];

// Verificação determinística: o input de ferramenta do modelo deve corresponder a este schema.
const OrderArgs = z.object({ orderId: z.number().int().positive() });

async function runOrder(orderId: number) {
  // Substituto para uma consulta real.
  return { orderId, status: "shipped", eta: "2026-03-04" };
}

export async function harness(userMessage: string) {
  const messages: Anthropic.MessageParam[] = [
    { role: "user", content: userMessage },
  ];

  // Limite de turnos: o guardrail mais importante contra loops infinitos.
  for (let turn = 0; turn < 6; turn++) {
    const res = await client.messages.create({
      model: "claude-sonnet-4-6",
      max_tokens: 1024,
      system: "You are an order-status assistant. Use tools when asked about orders.",
      tools,
      messages,
    });

    const toolUse = res.content.find(
      (b): b is Anthropic.ToolUseBlock => b.type === "tool_use"
    );
    if (!toolUse) return res.content; // Sem chamada de ferramenta → o modelo respondeu.

    messages.push({ role: "assistant", content: res.content });

    let observation: string;
    const parsed = OrderArgs.safeParse(toolUse.input);
    if (!parsed.success) {
      // Verificação falhou: retorna o erro COMO uma observação, não lança exceção.
      observation = `Invalid arguments: ${parsed.error.message}`;
    } else {
      try {
        observation = JSON.stringify(await runOrder(parsed.data.orderId));
      } catch (e) {
        observation = `Tool error: ${(e as Error).message}`; // também é uma observação
      }
    }

    messages.push({
      role: "user",
      content: [{ type: "tool_result", tool_use_id: toolUse.id, content: observation }],
    });
  }
  return [{ type: "text", text: "Could not complete the request." }];
}

Quatro decisões de design nessas ~50 linhas carregam a maior parte da confiabilidade. O loop for com limite de turnos é o loop de orquestração e o guardrail anti-loop. A ferramenta única mantém o schema de ferramentas pequeno. O safeParse do Zod é a verificação determinística que captura argumentos alucinados antes que eles atinjam seu backend. E tanto as falhas de validação quanto os erros de runtime são retornados como observações, não lançados como exceções — para que o modelo possa se corrigir em vez de a execução ser encerrada. A mecânica de uso de ferramentas da Anthropic está documentada no guia de uso de ferramentas; o loop equivalente com o SDK da OpenAI usa tool_calls e mensagens com role: "tool".

Por que desenvolvedores frontend controlam mais do harness do que imaginam?

Desenvolvedores frontend já são donos de um harness sempre que publicam um widget de chat com IA, um assistente de busca integrado ao produto ou uma UI de copiloto — são apenas harnesses mais superficiais do que os agênticos. A maioria das falhas de que os usuários reclamam (loops, chamadas de ferramentas alucinadas, contexto perdido, restrições ignoradas) são falhas de harness, não falhas de modelo. Quando uma equipe de frontend publica uma funcionalidade de IA, a escolha do modelo é uma decisão entre muitas, e as decisões de harness — escopo das ferramentas, qual contexto carregar, o que verificar — costumam receber menos revisão de design do que merecem.

O mapeamento é direto. Um usuário que vê o assistente “regenerar” a mesma resposta errada está observando um loop de orquestração sem verificação. Um usuário cuja restrição declarada desaparece dois turnos depois está diante de uma lacuna de estado e gerenciamento de contexto. Uma chamada de ferramenta que dispara com um argumento inválido e retorna uma resposta confusa é um schema check ausente — exatamente o passo safeParse descrito acima. Nenhum desses problemas é resolvido trocando o modelo. Eles são resolvidos ajustando o wrapper que você já controla.

Qual deve ser a espessura do meu harness? Quatro decisões que equipes de frontend controlam

Uma equipe de frontend que publica uma funcionalidade de IA em um produto controla, na prática, quatro decisões de harness: escopo das ferramentas, estratégia de contexto, loops de verificação e espessura do harness. A lista mais ampla do setor — agente único vs. multi-agente, ReAct vs. plan-and-execute, permissões, execução durável, governança de frota — pertence a camadas de infraestrutura que a maioria dos widgets de chat nunca alcança.

  1. Escopo das ferramentas — comece com menos de 10 ferramentas e expanda com cautela. Dar ao agente mais ferramentas do que ele precisa degrada o desempenho de forma consistente, porque cada schema de ferramenta adicional consome contexto e aumenta a probabilidade de uma chamada espúria. O resultado da Vercel é a evidência central: remover 80% das ferramentas melhorou tudo.

  2. Estratégia de contexto — compactação e recuperação just-in-time em vez de encher a janela. Não pré-carregue toda a base de conhecimento no prompt. Resuma turnos antigos quando se aproximar do limite da janela e busque documentos sob demanda. As orientações de context engineering da Anthropic definem o objetivo como o menor conjunto de tokens de alto valor.

  3. Loops de verificação — todo harness precisa de pelo menos uma verificação determinística antes de retornar o output ao usuário. Um validador de schema, uma regex, um teste unitário — algo que o harness possa executar sem depender do julgamento do próprio modelo. Sem isso, o agente não tem como saber que está errado. De acordo com a divisão computacional/inferencial de Böckeler, comece com uma verificação computacional barata; adicione um LLM como juiz apenas quando a correção semântica exigir.

  4. Espessura do harness — comece fino e adicione estrutura apenas quando um padrão de falha se repetir. Não pré-construa orquestração para falhas que você ainda não viu. Adicione um retry, um guardrail ou um passo de verificação quando uma falha específica aparecer mais de uma vez.

Assistir a session replays de uma funcionalidade de IA em produção é uma das formas mais rápidas de avaliar a qualidade do harness a partir do comportamento do usuário, porque as assinaturas diagnósticas são visíveis sem nenhuma telemetria no nível do modelo. Reformulações repetidas da mesma solicitação sinalizam contexto perdido ou um loop de verificação que nunca dispara. Abandono no meio de uma tarefa de múltiplos passos frequentemente se origina de um erro de ferramenta silenciado que se manifesta como uma resposta vaga. O comportamento de copiar e editar o output sinaliza uma lacuna de verificação — um output que passou pelas verificações do harness, mas falhou na avaliação do usuário. Cliques repetidos em “regenerar” ou “tentar novamente” são a assinatura de um harness em loop que não consegue detectar seu próprio estado de falha.

Para onde o design de harness está caminhando?

Os modelos agora são pós-treinados com seus harnesses no ciclo — como a LangChain observa em sua discussão sobre arquitetura de agent harness, produtos como Claude Code e Codex combinam treinamento de modelo e design de harness em um ciclo de feedback — o que significa que o harness não é mais um wrapper intercambiável, mas uma parte co-evoluída da superfície do produto. A implicação para os desenvolvedores é que o harness está se tornando parte do produto que você projeta, não um adaptador genérico que você pode transferir de um modelo para outro sem alterações.

Isso oferece um teste claro de preparação para o futuro, extraído da metáfora do scaffolding: se o seu design escala bem com um modelo mais robusto — mesmo harness, melhores resultados — ele é sólido. Se ele precisa de mais scaffolding para compensar à medida que o modelo melhora, o harness está mascarando um problema de modelo ou de tarefa que você deveria resolver em outro lugar. O scaffolding, assim como o da construção civil, deve ser removido quando a estrutura se sustenta por conta própria.

Da próxima vez que sua funcionalidade de IA entrar em loop, esquecer algo ou retornar algo confidentemente errado, audite o harness antes de auditar o modelo. Comece pelas quatro decisões acima — escopo das ferramentas, estratégia de contexto, uma verificação determinística e espessura — e adicione a menor quantidade de estrutura que faça a falha parar de se repetir.

Perguntas Frequentes

Qual é a diferença entre harness e scaffold?

Os termos são usados de forma intercambiável na prática; ambos se referem a todo o código, configuração e lógica de execução que envolve o modelo e não é o modelo em si. 'Scaffold' é o termo mais comum na literatura de benchmarks, como na comparação entre o CORE-Agent e o scaffold do Claude Code no Princeton, enquanto 'harness' é preferido em contextos de produção e SDK. Vivek Trivedy, da LangChain, colapsa a distinção com a regra: se você não é o modelo, você é o harness.

Devo retornar um erro de ferramenta ao modelo ou lançá-lo no meu harness?

Retorne o erro ao modelo como uma observação em vez de lançá-lo como exceção. Lançar a exceção encerra a execução; retornar o erro como um tool result permite que o modelo veja o que deu errado e se autocorrija no próximo turno. Isso importa porque os erros se acumulam em tarefas de múltiplos passos, onde uma tarefa de 10 passos com 99% de sucesso por passo cai para aproximadamente 90% de sucesso de ponta a ponta. Tanto as falhas de validação de schema quanto as exceções de runtime devem ser capturadas e devolvidas como observações, nunca como exceções não tratadas.

Adicionar mais ferramentas melhora o desempenho do agente?

Não, adicionar mais ferramentas degrada o desempenho de forma consistente a partir de um certo ponto. Cada schema de ferramenta consome tokens da janela de contexto e aumenta a probabilidade de uma chamada de ferramenta espúria ou incorreta. A equipe v0 da Vercel removeu 80% das ferramentas do agente e observou a taxa de sucesso subir de 80% para 100% e o uso médio de tokens cair 37% no mesmo modelo. A regra prática é começar com menos de 10 ferramentas e expandir apenas quando uma lacuna real aparecer.

Posso trocar modelos no mesmo harness sem alterações?

Cada vez menos. Como a LangChain observa em sua discussão sobre arquitetura de agent harness, produtos como Claude Code e Codex combinam treinamento de modelo e design de harness em um ciclo de feedback. Isso torna o harness uma parte co-evoluída da superfície do produto, e não um adaptador genérico. Um teste útil de preparação para o futuro é verificar se o seu design escala bem com um modelo mais robusto no mesmo harness; se ele precisa de mais scaffolding para compensar à medida que o modelo melhora, o harness está mascarando um problema mais profundo.

Understand every bug

Uncover frustrations, understand bugs and fix slowdowns like never before with OpenReplay — self-hosted, with full data ownership.

Star on GitHub

We use cookies to improve your experience. By using our site, you accept cookies.