🧩 Exercícios: Structured Outputs e Validação com Pydantic
Extra Inteligência Artificial • Trilha Progressiva em 4 Níveis
🧭 Navegação Pedagógica
-
📖 Teoria do Capítulo 💻 Exemplos 📊 Slides 🧠 Quiz
🎯 Nível 1: Fundamentos
Problema 12.1 — Modelo Pydantic para Extração de Faturas
Contexto: Construir um esquema de dados Pydantic rigoroso para validar informações extraídas de notas fiscais por um modelo de IA.
Requisitos de Execução:
- Definir o modelo
FaturaExtraidacom os campos:numero_nf(str),cnpj_emissor(str com validação de 14 dígitos),valor_total(float estritamente positivo) eitens(lista de strings com no mínimo 1 item). - Testar a validação com um payload JSON válido e um inválido (valor negativo).
- Exibir o objeto instanciado com sucesso.
Resultado Esperado
Validação Pydantic Concluída:
NF: 2026-9901 | Emissor: 12345678000199 | Total: R$ 1580.50 | Itens: 2
📤 Instruções de Entrega (Microsoft Teams)
- Salve o arquivo como:
Atividade_12_1_SeuNome - Envie na tarefa:
Atividade Cap 12 - Structured Outputs e Pydantic
🔑 Gabarito de Código & Solução Comentada
# pydantic_invoice.py
from pydantic import BaseModel, Field, field_validator
from typing import List
class FaturaExtraida(BaseModel):
numero_nf: str
cnpj_emissor: str = Field(..., min_length=14, max_length=14)
valor_total: float = Field(..., gt=0.0)
itens: List[str] = Field(..., min_length=1)
if __name__ == "__main__":
dados_validos = {
"numero_nf": "2026-9901",
"cnpj_emissor": "12345678000199",
"valor_total": 1580.50,
"itens": ["Licença Software", "Suporte Cloud"]
}
fatura = FaturaExtraida(**dados_validos)
print("Validação Pydantic Concluída:")
print(f"NF: {fatura.numero_nf} | Emissor: {fatura.cnpj_emissor} | Total: R$ {fatura.valor_total:.2f} | Itens: {len(fatura.itens)}")
🎯 Nível 2: Prática
Problema 12.2 — Extração com Enums e Campos Opcionais
Crie um modelo para classificação de tickets de suporte com CategoriaEnum (BUG, DUVIDA, FINANCEIRO), urgencia (1 a 5) e sugestao_solucao opcional.
🔑 Gabarito de Código & Solução Comentada
# ticket_classification.py
from enum import Enum
from typing import Optional
from pydantic import BaseModel, Field
class CategoriaTicket(str, Enum):
BUG = "BUG"
DUVIDA = "DUVIDA"
FINANCEIRO = "FINANCEIRO"
class TicketSuporte(BaseModel):
resumo: str
categoria: CategoriaTicket
urgencia: int = Field(..., ge=1, le=5)
sugestao_solucao: Optional[str] = None
🎯 Nível 3: Integração
Problema 12.3 — Loop de Auto-Correção de JSON com Instructor
Simule a lógica da biblioteca Instructor: quando o LLM devolve um JSON com erro de validação (ex: email sem @), o sistema captura o ValidationError, monta um novo prompt corretivo e obtém a versão corrigida.
🔑 Gabarito de Código & Solução Comentada
# instructor_retry_loop.py
from pydantic import BaseModel, EmailStr, ValidationError
class UsuarioExtraido(BaseModel):
nome: str
email: EmailStr
def extrair_com_auto_correcao(tentativas_mock):
for i, payload in enumerate(tentativas_mock, 1):
try:
user = UsuarioExtraido(**payload)
print(f"Sucesso na tentativa {i}: {user.email}")
return user
except ValidationError as err:
print(f"Tentativa {i} falhou: {err.errors()[0]['msg']}. Solicitando correção ao LLM...")
return None
🎯 Nível 4: Desafio
Problema 12.4 — Schema Generation para Injeção em Function Calling
Escreva uma função que receba dinamicamente qualquer classe Pydantic e gere o esquema JSON Schema compatível com a API de ferramentas da OpenAI/Anthropic (tools=[{"type": "function", "function": ...}]).
🔑 Gabarito de Código & Solução Comentada
# pydantic_to_tool_schema.py
from pydantic import BaseModel
def converter_pydantic_para_ferramenta_llm(modelo: type[BaseModel]):
schema = modelo.model_json_schema()
return {
"type": "function",
"function": {
"name": modelo.__name__,
"description": modelo.__doc__ or f"Extrai estrutura {modelo.__name__}",
"parameters": schema
}
}