ZynzapAPI

Cobrança e cotações

Operações pagas pedem uma cotação antes. Você conhece o custo máximo, executa com o quoteId e só paga o que foi usado.

Leituras e configurações são gratuitas. Envios, campanhas, aquecimento e IA são pagos e seguem sempre dois passos:

  1. Cotar em POST /billing/quotes com a operação e o request exatos. A resposta traz o custo máximo e um quoteId.
  2. Executar em POST /rpc/{Operação} com o mesmo request e "billing": {"quoteId": "..."}.

Sem cotação a operação falha com 428 e reason: BILLING_QUOTE_REQUIRED. O preço é o mesmo do painel; você nunca paga mais do que a cotação mostrou.

OperaçãoTarifa (kind)
SendMessage, SendImageMessage, SendVoiceNote, SendVideoMessage, SendDocumentMessage, SendConversationMessage (e o atalho POST /messages/send)send
StartCampaign, StartCampaignWithTemplate, ResumeCampaigncampaign
StartWarmup, ResumeWarmupRunwarmup
CorrectMessage, SummarizeConversation, SuggestReply, SuggestLeadClassificationai

1. Cotar

curl -X POST "https://api.zynzap.com.br/v1/billing/quotes" \
  -H "Authorization: Bearer $ZYNZAP_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "method": "SendMessage",
  "request": {
    "session_id": "8c1f7a52-4d1e-4b8a-9a43-2f6f5d0c9e11",
    "to_jid": "5511987654321",
    "text": "Seu pedido #1234 saiu para entrega."
  }
}'
Campo da respostaSignificado
quoteIdEnvie em billing.quoteId ao executar.
kindTarifa aplicada: send, campaign, warmup ou ai.
maxMicrobrlCusto máximo em micro-reais (1 real = 1.000.000; 50000 = R$ 0,05).
coveredMicrobrlQuanto já está coberto por saldo, franquia do plano e excedente autorizado.
monthlyOverageMicrobrlParte que entra no excedente mensal (cartão), se habilitado.
dueCentsValor que falta, em centavos. Maior que zero: a execução vai falhar com 402 até haver saldo.
coverageinbox_window (resposta grátis na janela de 24 horas), waived (isenção) ou null.
expiresAtA cotação vale 15 minutos.

paymentMode (opcional) escolhe a origem do dinheiro: budget (padrão: saldo, franquia e excedente da conta) ou individual (a operação é paga à parte).

2. Executar

curl -X POST "https://api.zynzap.com.br/v1/rpc/SendMessage" \
  -H "Authorization: Bearer $ZYNZAP_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "request": {
    "session_id": "8c1f7a52-4d1e-4b8a-9a43-2f6f5d0c9e11",
    "to_jid": "5511987654321",
    "text": "Seu pedido #1234 saiu para entrega."
  },
  "billing": {
    "quoteId": "0b8f2c1e-3a4d-4e5f-8a9b-1c2d3e4f5a6b"
  }
}'

A cotação fica presa ao conteúdo: operação, request (texto, mídia, destinatários), números envolvidos e configuração. Mudou qualquer coisa? Peça outra (409 BILLING_QUOTE_MISMATCH). Cada cotação executa uma única vez (veja Idempotência).

Janela grátis de 24 horas no atendimento

Responder pelo atendimento (SendConversationMessage) uma conversa individual em que o cliente escreveu nas últimas 24 horas sai de graça: a cotação volta com coverage: "inbox_window" e custo zero. Ainda assim você precisa cotar e enviar o quoteId (a regra é avaliada na hora). Mensagens que você inicia (SendMessage, campanhas) e conversas em grupo são cobradas normalmente.

curl -X POST "https://api.zynzap.com.br/v1/billing/quotes" \
  -H "Authorization: Bearer $ZYNZAP_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "method": "SendConversationMessage",
  "request": {
    "conversation_id": "5f0e1d2c-3b4a-4596-8877-66554433aa11",
    "session_id": "8c1f7a52-4d1e-4b8a-9a43-2f6f5d0c9e11",
    "message_type": "text",
    "text": "Claro! Já verifico para você.",
    "idempotency_key": "resposta-0001"
  }
}'

Quanto é cobrado de verdade

  • O custo é reservado na execução e consumido conforme o transporte aceita as mensagens. O que não for usado (falhas antes do envio, campanha cancelada) volta para o saldo.
  • Mensagem aceita pelo WhatsApp é cobrada mesmo que nunca seja entregue ou lida: aceitação não garante entrega.
  • Em resultado incerto (OUTCOME_UNCERTAIN), o valor fica reservado até a confirmação; consulte o estado antes de reenviar.
  • Campanhas cotam o custo máximo da campanha inteira; retomar uma campanha pede nova cotação do restante.

Erros de cobrança

reasonHTTPO que fazer
BILLING_QUOTE_REQUIRED428Cote e envie billing.quoteId.
BILLING_QUOTE_INVALID400quoteId precisa ser o UUID devolvido pela cotação.
BILLING_QUOTE_EXPIRED409Passaram 15 minutos: cote de novo.
BILLING_QUOTE_MISMATCH409O request mudou: cote com o corpo final.
BILLING_IDEMPOTENCY_CONFLICT409A cotação já foi usada com outro conteúdo.
BILLING_PAYMENT_REQUIRED402Saldo insuficiente: compre créditos ou habilite o excedente no painel (Plano e consumo).
BILLING_METHOD_INVALID400A operação não é paga (não precisa de cotação).

Veja o guia Tratar cobrança na sua integração para um fluxo completo, com novas tentativas e checagem de saldo.