Agentes de IA e Chamadas de Função: Construindo Ferramentas para LLMs
Você está construindo um agente de IA que precisa buscar dados em tempo real, realizar cálculos ou interagir com APIs externas. Mas como preencher a lacuna entre a geração de texto do LLM e a execução real de código? Chamadas de função (também conhecidas como uso de ferramentas) é a resposta. Elas permitem que os LLMs solicitem ações específicas, e seu código as execute. Este guia mostra como projetar, implementar e depurar chamadas de função para agentes de IA.
O que é Chamada de Função?
Chamada de função é um mecanismo no qual um LLM pode emitir uma solicitação estruturada para chamar uma função que você definiu. Em vez de gerar texto livre, o modelo retorna um objeto JSON com o nome da função e os argumentos. Sua aplicação então executa a função e realimenta o resultado no modelo. Isso permite que os agentes realizem ações além da geração de texto, como consultar bancos de dados, enviar e-mails ou chamar APIs.
Os principais provedores de LLM, como OpenAI, Anthropic e Google, suportam chamadas de função. A ideia central é consistente: você descreve as ferramentas disponíveis, o modelo decide quando usá-las e você lida com a execução.
Projetando Ferramentas para LLMs
Ferramentas bem projetadas são cruciais para um comportamento confiável do agente. Siga estes princípios:
- Nomes e descrições claros: Use nomes descritivos para funções e descrições detalhadas. O LLM depende disso para escolher a ferramenta certa.
- Parâmetros simples: Mantenha os parâmetros mínimos e use tipos padrão (string, number, boolean, array, object). Evite estruturas aninhadas complexas quando possível.
- Idempotência: Quando possível, projete ferramentas para serem idempotentes (seguras para repetir) para lidar com falhas de forma elegante.
- Tratamento de erros: Retorne mensagens de erro informativas para que o LLM possa ajustar sua abordagem.
Exemplo: Ferramenta de Clima
Aqui está uma definição simples de ferramenta no formato JSON schema, comumente usada com a API da OpenAI:
{
"name": "get_weather",
"description": "Get the current weather for a given city",
"parameters": {
"type": "object",
"properties": {
"city": {
"type": "string",
"description": "The city name, e.g., San Francisco"
},
"unit": {
"type": "string",
"enum": ["celsius", "fahrenheit"],
"description": "Temperature unit"
}
},
"required": ["city"]
}
}
Implementando Chamadas de Função: Passo a Passo
Vamos construir um loop de agente mínimo usando a API da OpenAI (o padrão se aplica a outros provedores).
1. Defina Suas Ferramentas
Crie uma lista de esquemas de ferramentas e um mapeamento de nomes de funções para funções Python reais.
import json
import openai
# Esquemas de ferramentas
tools = [
{
"type": "function",
"function": {
"name": "get_weather",
"description": "Get current weather for a city",
"parameters": {
"type": "object",
"properties": {
"city": {"type": "string"},
"unit": {"type": "string", "enum": ["celsius", "fahrenheit"]}
},
"required": ["city"]
}
}
}
]
# Funções reais
def get_weather(city: str, unit: str = "celsius") -> dict:
# Na realidade, chame uma API de clima
return {"city": city, "temperature": 22, "unit": unit, "condition": "sunny"}
# Mapeie nomes para funções
function_map = {
"get_weather": get_weather
}
2. Crie o Loop do Agente
O loop do agente envia mensagens para o LLM, verifica chamadas de ferramentas, executa-as e repete até que o modelo retorne uma resposta final.
def run_agent(user_message: str):
messages = [{"role": "user", "content": user_message}]
while True:
response = openai.ChatCompletion.create(
model="gpt-4",
messages=messages,
tools=tools,
tool_choice="auto"
)
message = response.choices[0].message
messages.append(message)
# Se não houver chamadas de ferramentas, retorne o conteúdo
if not message.get("tool_calls"):
return message["content"]
# Execute cada chamada de ferramenta
for tool_call in message.tool_calls:
function_name = tool_call.function.name
arguments = json.loads(tool_call.function.arguments)
if function_name in function_map:
result = function_map[function_name](**arguments)
else:
result = {"error": f"Unknown function: {function_name}"}
# Anexe o resultado da ferramenta às mensagens
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": json.dumps(result)
})
Este loop continua até que o LLM produza uma resposta sem chamadas de ferramentas, indicando que tem informações suficientes.
3. Trate Erros e Casos Extremos
Agentes do mundo real devem lidar com:
- Argumentos inválidos: Capture exceções ao analisar argumentos ou chamar funções.
- Ferramentas desconhecidas: Retorne uma mensagem de erro ao LLM para que ele possa se corrigir.
- Timeouts: Defina timeouts para chamadas de API externas para evitar travamentos.
- Limites de taxa: Implemente tentativas com backoff exponencial.
Melhores Práticas para Agentes Confiáveis
- Limite o número de ferramentas: Muitas ferramentas confundem o modelo. Agrupe funções relacionadas ou use um roteador.
- Valide as entradas: Sanitize e valide todos os argumentos antes da execução.
- Registre tudo: Registre chamadas de ferramentas e resultados para depuração e auditoria.
- Teste com prompts variados: Garanta que o agente selecione as ferramentas certas em diferentes cenários.
- Forneça alternativas: Se uma ferramenta falhar, o agente deve tentar alternativas ou pedir esclarecimentos.
Comparação do Suporte a Chamadas de Função
| Provedor | Nome do Recurso | Formato |
|---|---|---|
| OpenAI | Function Calling | JSON Schema |
| Anthropic | Tool Use | JSON Schema |
| Function Calling | OpenAPI Schema |
Padrões Avançados
À medida que seu agente cresce, considere estes padrões:
- Chamadas de ferramentas paralelas: Alguns modelos podem solicitar várias ferramentas de uma vez. Execute-as simultaneamente para maior velocidade.
- Humano no loop: Para ações sensíveis (por exemplo, enviar dinheiro), exija aprovação humana antes da execução.
- Memória: Armazene o histórico de conversas e resultados de ferramentas para fornecer contexto em sessões longas.
- Roteamento de ferramentas: Use um classificador leve para selecionar ferramentas relevantes antes de chamar o LLM principal.
Depurando Chamadas de Função
Quando as coisas dão errado, verifique:
- As descrições das ferramentas estão claras e inequívocas?
- Os nomes e tipos dos parâmetros estão corretos?
- O modelo tem contexto suficiente para escolher a ferramenta certa?
- Você está lidando corretamente com os resultados das ferramentas (por exemplo, serialização JSON)?
Use registro de logs para capturar o histórico completo de mensagens e chamadas de ferramentas. Muitas vezes, o problema é uma incompatibilidade entre os argumentos esperados e os reais.
FAQ
Qual é a diferença entre chamada de função e uso de ferramenta?
Eles se referem ao mesmo conceito. A OpenAI chama de "function calling", enquanto a Anthropic usa "tool use". Ambos permitem que os LLMs solicitem a execução de funções externas.
Posso usar chamadas de função com modelos de código aberto?
Sim, alguns modelos de código aberto como o Llama 3.1 suportam chamadas de função, e frameworks como LangChain fornecem abstrações. No entanto, o suporte varia, e você pode precisar de ajuste fino ou usar formatos de prompt específicos.
Como evito que o LLM chame funções perigosas?
Nunca exponha funções perigosas diretamente. Use listas de permissões, valide entradas e implemente verificações de permissão. Para operações sensíveis, exija confirmação humana antes da execução.
Pronto para construir seu próprio agente de IA? Comece definindo uma ferramenta simples e testando o loop do agente. Para mais ferramentas de desenvolvedor, confira nosso Formatador JSON para depurar payloads de chamadas de ferramentas.