Webhook do WhatsApp: como configurar e validar (guia técnico)
Guia técnico do webhook da WhatsApp Cloud API: verificação com hub.challenge, assinatura X-Hub-Signature-256, estrutura do payload (messages e statuses) e boas práticas de produção.
O webhook do WhatsApp é a URL HTTPS do seu sistema que a Meta chama para entregar eventos da Cloud API: mensagens recebidas dos clientes e status de entrega (enviada, entregue, lida, falhou). A configuração tem duas partes: responder ao desafio de verificação (GET com hub.challenge) e validar a assinatura HMAC de cada notificação (header X-Hub-Signature-256). Quem usa uma plataforma como a Wizebot não precisa implementar isso — o webhook da Meta já vem tratado, e a plataforma expõe webhooks prontos para os seus sistemas.
Enviar mensagem pela Cloud API é a parte fácil. O que fecha o ciclo — receber respostas e saber o que foi entregue — é o webhook. Este guia cobre a implementação correta, incluindo as pegadinhas que não estão óbvias na documentação.
O que é o webhook do WhatsApp
Os requisitos são rígidos: URL pública, HTTPS com certificado válido (autoassinado não funciona) e resposta rápida. A configuração é feita no App Dashboard da Meta, assinando o campo messages.
Parte 1 — A verificação (GET)
Ao cadastrar a URL, a Meta faz uma única requisição GET com três parâmetros de query: hub.mode=subscribe, hub.verify_token (a string secreta que você definiu no painel) e hub.challenge (uma string aleatória).
Seu endpoint deve validar o token e devolver HTTP 200 com o valor puro de hub.challenge no corpo — sem JSON, sem aspas:
app.get("/webhook", (req, res) => {
const { "hub.mode": mode, "hub.verify_token": token, "hub.challenge": challenge } = req.query;
if (mode === "subscribe" && token === process.env.VERIFY_TOKEN) {
return res.status(200).send(challenge);
}
return res.sendStatus(403);
});
Qualquer outra resposta e o cadastro falha — este é o primeiro ponto onde integrações travam.
Parte 2 — A assinatura (POST)
Toda notificação chega com o header X-Hub-Signature-256: um HMAC-SHA256 do corpo da requisição, usando o App Secret como chave. Validar é obrigatório em produção — sem isso, qualquer um que descubra sua URL pode injetar mensagens falsas.
As duas pegadinhas clássicas:
- Valide sobre o corpo bruto (raw body), antes de qualquer parse de JSON. A Meta assina o payload com caracteres especiais em unicode escapado — se você fizer parse e re-serializar, o hash nunca vai bater.
- Use comparação timing-safe (
crypto.timingSafeEqualno Node,hmac.compare_digestno Python).
Parte 3 — O payload: messages vs. statuses
Tudo chega no mesmo envelope entry → changes → value:
{
"object": "whatsapp_business_account",
"entry": [{
"id": "WABA_ID",
"changes": [{
"field": "messages",
"value": {
"metadata": { "phone_number_id": "..." },
"messages": [{ "from": "5511...", "id": "wamid...", "type": "text", "text": { "body": "Oi!" } }]
}
}]
}]
}
O que diferencia os eventos é qual array existe dentro de value:
| Array em value | Significado | Campos-chave |
|---|---|---|
messages | Mensagem recebida do cliente | from, type, corpo por tipo (text, image...) |
statuses | Atualização de mensagem enviada | status (sent/delivered/read/failed), id (wamid) |
errors | Erro no nível da conta | code, title, error_data |
O wamid retornado no envio é a chave para correlacionar cada status. E atenção: falhas de entrega (como os erros 131026 e 131048) chegam como statuses com status: "failed" e um array errors — se você não tratar esse caso, suas mensagens somem silenciosamente.
Boas práticas de produção
- Responda 200 imediatamente e processe depois (fila). Referência prática: menos de 5 segundos. Falhas consecutivas fazem a Meta reenviar com backoff e podem desabilitar a assinatura do webhook.
- Não confie na ordem — eventos podem chegar fora de sequência (um
readantes dodelivered). - Trate duplicatas — a Meta reenvia notificações não confirmadas; use o
wamidcomo chave de idempotência. - Registre o payload cru dos primeiros dias — é a única forma de depurar campos inesperados.
Precisa mesmo implementar tudo isso?
Se você está construindo um produto sobre a API da Meta, sim — e este guia mais o de integração cobrem o essencial. Mas se o objetivo é conectar o WhatsApp a sistemas de vendas e atendimento, há um atalho: a Wizebot já implementa e mantém o webhook da Meta (verificação, assinatura, retries, correlação de status) e expõe webhooks e API própria para os seus sistemas — você recebe eventos limpos e prontos, integrados a Hotmart, Shopify, Pipedrive, Google Sheets e mais de 50 plataformas.
Perguntas frequentes
Perguntas frequentes
O webhook do WhatsApp funciona em localhost?
Por que meu webhook valida mas não recebe mensagens?
Como sei se uma mensagem enviada falhou?
A validação da assinatura X-Hub-Signature-256 é obrigatória?
Webhook bem feito é o que separa uma integração de WhatsApp confiável de uma que perde mensagens em silêncio. Se preferir pular a infraestrutura e ir direto para a operação, a Wizebot entrega a API oficial com todo esse encanamento pronto.