Antonnia Docs

Tratamento de Erros

Códigos de erro, estratégias de retry e recuperação de falhas

Este guia cobre cenários comuns de erro e como tratá-los na sua integração de canal.

Códigos de status HTTP

CodeSignificadoAção
200SucessoProcessar a resposta
201CriadoRecurso criado com sucesso
400Requisição inválidaVerifique o corpo da requisição — tipo de conteúdo inválido, sessão não aberta, etc.
401Não autorizadoVerifique seu token de API
404Não encontradoSessão ou mensagem não existe
422Erro de validaçãoO corpo da requisição falhou na validação — verifique tipos e valores dos campos

Respostas de erro comuns

401 Unauthorized

{
  "detail": "Invalid or expired token"
}

Verifique se o header Authorization: Bearer sk_live_... está definido corretamente e se o token não expirou.

404 Not Found

{
  "detail": "Session not found"
}

O ID da sessão não existe ou pertence a uma organização diferente.

400 Bad Request — Sessão não aberta

{
  "detail": "Session is not open"
}

Você está tentando responder ou criar mensagens em uma sessão fechada. Crie uma nova sessão.

400 Bad Request — Sem agente de IA

{
  "detail": "Session has no agent"
}

A sessão não tem um agente atribuído. Atribua um via POST /sessions/{id}/transfer ou crie uma nova sessão com agent_id.

422 Validation Error

{
  "detail": [
    {
      "loc": ["body", "content", "type"],
      "msg": "value is not a valid enumeration member",
      "type": "type_error.enum"
    }
  ]
}

O corpo da requisição não corresponde ao schema esperado. Verifique os nomes dos campos, tipos e valores permitidos.

Estratégia de retry

Quando fazer retry

  • Erros 5xx — problemas no servidor, faça retry com backoff exponencial
  • 429 Too Many Requests — rate limited, faça retry após o delay indicado
  • Erros de rede — problemas transitórios de conectividade

Quando NÃO fazer retry

  • Erros 4xx (exceto 429) — erros do cliente que não serão resolvidos com retry
  • Falhas na entrega de mensagens — reporte o status de falha em vez de tentar novamente

Exemplo de backoff exponencial

import asyncio
import httpx

async def api_call_with_retry(method: str, url: str, max_retries: int = 3, **kwargs):
    for attempt in range(max_retries):
        try:
            response = httpx.request(method, url, headers=HEADERS, **kwargs)
            if response.status_code < 500:
                return response
        except httpx.TransportError:
            pass

        if attempt < max_retries - 1:
            await asyncio.sleep(2 ** attempt)  # 1s, 2s, 4s

    raise Exception(f"API call failed after {max_retries} retries")

Tratamento de condições de corrida

Status de entrega antes da criação da mensagem

Confirmações de entrega do seu canal podem chegar antes da Antonnia finalizar a criação da mensagem. Se você não encontrar a mensagem pelo provider_message_id, isso é esperado — registre no log e ignore:

messages = httpx.post(
    f"{BASE_URL}/sessions/{session_id}/messages/search",
    headers=HEADERS,
    json={"provider_message_id": channel_msg_id},
).json()

if not messages:
    logger.info("Message not yet created, skipping status update",
                provider_message_id=channel_msg_id)
    return

Criação duplicada de sessões

Sem locking, mensagens simultâneas do mesmo contato podem criar sessões duplicadas. Sempre use um lock distribuído ao redor do get-or-create de sessão:

async with redis_lock(f"lock:mychannel:{contact_id}:{instance_id}", timeout=30):
    session = await get_or_create_session(contact_id, instance_id)

Tratamento de erros específicos do canal

Falhas no download de mídia

Se o download de mídia do seu canal falhar, use um placeholder de texto como fallback:

try:
    media_url = await download_and_host(channel_media_url)
    content = {"type": "image", "url": media_url}
except Exception:
    content = {"type": "text", "text": "[Image could not be loaded]"}

Erros na API do canal

Quando a API de envio do seu canal falhar, reporte a falha para a Antonnia:

try:
    channel_msg_id = await channel_api.send(instance_id, user_id, content)
    await update_delivery_status(message_id, "sent", channel_msg_id)
except ChannelAPIError as e:
    await update_delivery_status(
        message_id, "failed",
        error_code=e.code,
        error_message=str(e),
    )

Logging estruturado com contexto (session_id, message_id, detalhes do erro) torna muito mais fácil debugar problemas em produção. Use nível warning para erros esperados e nível exception para erros inesperados.

On this page