Guia prático de respostas estruturadas com LLMs
Entenda como usar respostas estruturadas com LLMs para gerar saídas mais previsíveis, validar dados, tratar erros de parsing e integrar IA em aplicações.
Resposta estruturada não é só pedir para a IA devolver JSON. É definir um contrato entre o modelo e a aplicação, validar esse contrato e decidir o que acontece quando a saída não vem no formato esperado.
Contexto
Nos guias anteriores da série, a ideia foi construir uma base para pensar em aplicações com IA de forma mais prática.
Primeiro, o foco foi RAG: quando uma aplicação precisa buscar contexto externo antes de responder. Depois, o foco foi chunking, embeddings e retrieval: como preparar e recuperar contexto antes de entregar esse material para o modelo.
Mas existe outro problema que aparece rápido quando a IA deixa de ser só uma conversa e começa a entrar em uma aplicação real: a resposta do modelo precisa virar dado.
Ela pode precisar preencher campos, alimentar uma tela, passar por uma regra, gerar uma ação sugerida, classificar uma mensagem, resumir uma solicitação, criar uma lista de próximos passos ou preparar algo para revisão humana.
Nesse cenário, uma resposta bonita não basta. Se o sistema espera um objeto com campos específicos, tipos definidos e valores possíveis, um parágrafo bem escrito pode ser inútil. Pior: pode parecer correto para uma pessoa, mas quebrar o fluxo da aplicação.
O problema
A pergunta central deste guia é: como usar respostas de LLM dentro de uma aplicação sem depender de texto livre e interpretação manual?
Pedir para o modelo "responder em JSON" pode parecer suficiente no começo. Em um protótipo simples, talvez até funcione. Mas, quando a saída entra em um fluxo de sistema, aparecem perguntas mais concretas.
- Quais campos são obrigatórios?
- Quais tipos são aceitos?
- Quais valores são válidos?
- O que acontece se um campo vier ausente?
- O sistema tenta de novo, mostra erro ou manda para revisão?
- Essa validação olha só o formato ou também a qualidade do conteúdo?
Sem responder essas perguntas, a integração fica frágil. O modelo gera alguma coisa, o código tenta interpretar, e a aplicação torce para a saída bater com o esperado.
Modelo mental
1contrato esperado2 -> geração da resposta3 -> validação4 -> uso no sistema ou fallbackO contrato esperado define o formato da saída. A geração orienta o modelo a responder nesse formato. A validação confere se a resposta recebida pode ser usada com segurança mínima. O fallback define o que acontece quando a saída não passa pela validação.
Resposta estruturada não é uma garantia de acerto. Ela é uma forma de deixar explícito o que o sistema esperava receber.
Texto livre, JSON e schema
Texto livre é quando o modelo responde em linguagem natural, sem formato rígido. JSON é um formato de dados que pode ser lido por código. Schema é a definição do formato esperado: quais campos existem, quais são obrigatórios, quais tipos são aceitos e quais limites precisam ser respeitados.
Um JSON pode estar bem formatado e ainda assim ser ruim para a aplicação.
1{2 "prioridade": "urgente",3 "resumo": "",4 "acoes_sugeridas": []5}Se o sistema só aceita `baixa`, `media` ou `alta` como prioridade, o valor `urgente` está fora do contrato. Se `resumo` é obrigatório e não pode ser vazio, o campo falhou. Se `acoes_sugeridas` precisa ter pelo menos um item, a lista vazia também precisa ser tratada.
Por isso, o ponto principal não é usar JSON. O ponto principal é definir um contrato que o sistema consiga validar.
Quando respostas estruturadas ajudam
Respostas estruturadas são úteis quando a saída do modelo precisa ser consumida por código.
- Extrair dados de uma mensagem.
- Classificar uma solicitação.
- Preencher campos de um formulário.
- Gerar uma lista de tarefas.
- Identificar intenção do usuário.
- Montar parâmetros para uma busca.
- Sugerir ações para revisão humana.
- Retornar blocos que a interface vai renderizar.
Exemplo prático
Imagine uma aplicação fictícia que recebe mensagens de suporte e usa IA para organizar a triagem.
1Não consigo acessar minha conta desde ontem. Já tentei redefinir a senha, mas o e-mail não chega.Uma resposta em texto livre poderia ser legível para uma pessoa, mas pouco prática para o sistema. Uma saída estruturada pode organizar o mesmo caso em campos úteis.
1{2 "tipo": "suporte",3 "categoria": "login",4 "prioridade": "media",5 "resumo": "Usuário não consegue acessar a conta e não recebe o e-mail de redefinição de senha.",6 "acoes_sugeridas": [7 "Verificar logs de envio de e-mail",8 "Confirmar se o endereço cadastrado está correto",9 "Checar tentativas recentes de login"10 ],11 "precisa_revisao_humana": true12}Agora a aplicação consegue filtrar por categoria, destacar prioridade, preencher uma tela, enviar para revisão, registrar o resumo e mostrar ações sugeridas sem precisar interpretar um parágrafo.
Quando texto livre ainda faz sentido
Nem toda resposta precisa ser estruturada. Texto livre pode ser suficiente quando o objetivo é conversar, explorar ideias, explicar um conceito, escrever um rascunho narrativo, resumir algo para leitura humana, gerar variações de copy ou apoiar uma decisão sem acionar fluxo automático.
O critério é simples: a aplicação precisa usar essa resposta como dado? Se sim, estrutura ajuda. Se não, texto livre pode ser suficiente.
Como pensar o schema
Um schema bom começa com a necessidade da aplicação, não com a resposta que parece mais bonita. Antes de pedir qualquer formato ao modelo, vale perguntar quais campos o sistema realmente precisa, quais valores são permitidos, quais campos podem ser opcionais e o que será exibido para o usuário.
1tipo: suporte | duvida | feedback | outro2categoria: login | pagamento | conta | produto | outro3prioridade: baixa | media | alta4resumo: texto curto obrigatório5acoes_sugeridas: lista de textos6precisa_revisao_humana: booleanoEsse contrato não precisa ser complexo para ser útil. Ele só precisa deixar claro o que a aplicação espera.
Validação: formato não é qualidade
Uma armadilha comum é achar que, se a resposta passou no parsing, ela está boa. Parsing, validação de formato e validação de qualidade são camadas diferentes.
- Parsing: o sistema conseguiu ler a saída?
- Validação de formato: os campos e tipos respeitam o contrato?
- Validação de qualidade: o conteúdo faz sentido, está correto e é útil para o caso?
Uma resposta pode ser JSON válido, passar no schema e ainda trazer uma classificação ruim. Respostas estruturadas ajudam na integração, mas não substituem evals, revisão humana e critérios de qualidade.
Erros comuns
Pedir JSON sem definir contrato
"Responda em JSON" é uma instrução, não um contrato. Se o prompt não define campos, tipos, valores aceitos e limites, o modelo pode inventar uma estrutura diferente a cada resposta.
Aceitar a resposta sem validar
Mesmo que o modelo costume acertar o formato, a aplicação não deve assumir que a saída sempre virá correta. Campos podem faltar, tipos podem mudar, listas podem vir vazias e valores podem sair do conjunto esperado.
Confundir estrutura com verdade
O schema ajuda a validar formato, não garante que o modelo entendeu o caso, usou o contexto certo ou classificou bem. Mesmo que o modelo devolva um JSON perfeito, ele pode ter usado um contexto recuperado fraco ou insuficiente.
Esconder falhas do usuário
Quando a resposta não passa na validação, a aplicação precisa lidar com isso de forma clara. Uma falha de parsing não deveria virar uma tela quebrada, uma ação automática errada ou uma mensagem confusa.
Fallback: o que fazer quando falha
Fallback é a parte que muita gente deixa para depois, mas ele deveria fazer parte do desenho desde o começo.
- Tentar novamente com uma instrução mais restrita.
- Retornar erro controlado.
- Pedir revisão humana.
- Usar um caminho manual.
- Salvar a resposta como pendente.
- Registrar o caso para análise.
O melhor fallback depende do risco. Se a saída apenas sugere tags para um rascunho interno, talvez uma nova tentativa seja suficiente. Se a saída influencia uma ação sensível, o caminho precisa ser mais conservador.
Exemplo prático de fluxo
11. receber mensagem do usuário22. montar prompt com o contrato esperado33. solicitar resposta estruturada44. tentar fazer parsing55. validar campos obrigatórios, tipos e valores aceitos66. se passar, usar os dados no sistema77. se falhar, aplicar fallback88. registrar o resultado para revisãoValidações mínimas podem conferir se `tipo` e `categoria` estão na lista permitida, se `prioridade` é `baixa`, `media` ou `alta`, se `resumo` não está vazio, se `acoes_sugeridas` é uma lista e se `precisa_revisao_humana` é booleano.
Essa validação ainda não diz se a triagem está perfeita. Mas já impede que uma saída malformada entre no restante do sistema como se estivesse tudo certo.
Como validar se está funcionando
Um bom começo é criar um conjunto pequeno de casos conhecidos. Para cada caso, registre a entrada original, a saída esperada, a saída recebida, erro de formato, erro de conteúdo, fallback aplicado e decisão humana quando existir.
1Entrada: "Não recebo o e-mail de redefinição de senha."2Esperado: categoria login, prioridade media, revisão humana true3Recebido: categoria conta, prioridade baixa, revisão humana false4Diagnóstico: formato válido, classificação fraca5Próximo ajuste: melhorar exemplos e critérios de prioridadeEsse registro separa dois tipos de problema: a resposta não pôde ser lida ou não respeitou o schema; ou a resposta respeitou o formato, mas não foi boa. Essa separação prepara o terreno para evals e harness.
Quando manter simples
Respostas estruturadas são úteis, mas não precisam virar excesso de engenharia. Talvez você não precise de um schema grande se a resposta é apenas apoio para leitura humana, se o fluxo ainda está em exploração, se a tarefa não aciona nada no sistema ou se uma revisão manual sempre acontece antes do uso.
1{2 "resumo": "texto curto",3 "precisa_revisao": true4}O objetivo não é deixar tudo mais complexo. É deixar explícito o contrato mínimo quando a aplicação precisa confiar em alguma forma de dado.
Aprendizados
- Resposta estruturada é útil quando a saída da IA precisa ser consumida por código.
- JSON é apenas um formato; o ponto principal é o contrato de saída.
- Schema ajuda a explicitar campos, tipos, obrigatoriedade e limites.
- Parsing, validação de formato e validação de qualidade são coisas diferentes.
- Uma resposta estruturada pode estar bem formatada e ainda estar errada.
- Fallback precisa ser pensado antes de a falha acontecer.
- Revisão humana continua importante em fluxos sensíveis.
- Registrar falhas ajuda a melhorar prompt, schema, evals e harness.
Limites e ressalvas
Este guia não tenta escolher uma API, SDK ou framework específico. Também não entra em validação avançada de dados, versionamento de schema ou comparação entre provedores.
Outro limite importante: resposta estruturada não resolve problema factual. Se o contexto recuperado é ruim, se o prompt está confuso ou se os critérios de qualidade não existem, o modelo ainda pode devolver uma saída ruim dentro de um formato válido.
Conclusão
Pedir para um LLM responder em JSON pode ser um começo, mas não é o suficiente. Em aplicações reais, a pergunta é mais ampla: qual contrato a aplicação espera receber?
Se a resposta precisa virar dado, a saída deve ser previsível, validável e tratável quando falha. Isso não elimina erro, mas tira parte da integração do campo da sorte.
Antes de usar a resposta da IA no sistema, defina o formato esperado, valide o que chegou e tenha um caminho claro quando o modelo não cumprir o contrato.
