Skip to Content
API de integração — v1
Webhooks

Webhooks

Webhooks notificam seu sistema em tempo real quando algo acontece com seus documentos fiscais — sem precisar ficar consultando a API.

Eventos

EventoQuando dispara
document.authorizedA NF-e/NFC-e/NFS-e foi autorizada pela SEFAZ/prefeitura
document.rejectedA emissão foi rejeitada pelo fisco
document.cancelledUm documento autorizado foi cancelado
document.inutilizedUm intervalo de numeração foi inutilizado

Cadastrar um endpoint

Crie um endpoint via API (escopo webhooks:write) ou pela tela Webhooks no painel. Selecione os eventos desejados — sem nenhum selecionado, o endpoint recebe todos.

curl -X POST https://api.conttrole.io/v1/webhooks \ -H "Authorization: Bearer ck_live_..." \ -H "Content-Type: application/json" \ -d '{ "url": "https://seu-sistema.com/webhooks/conttrole", "description": "Integração ERP", "events": ["DOCUMENT_AUTHORIZED", "DOCUMENT_CANCELLED"] }'

A resposta traz o secret de assinatura uma única vez — guarde-o.

A URL precisa ser https e apontar para um host público — endereços internos/privados (localhost, IPs de rede interna, metadata de cloud) são recusados por segurança (proteção contra SSRF).

Verificação de saúde no cadastro

Antes de salvar, a Conttrole faz um POST de verificação assinado para a URL informada (um evento webhook.ping, assinado igual aos eventos reais). O endpoint precisa responder 2xx em até 10s — caso contrário o cadastro é recusado com HTTP 422 (webhook_unreachable). Garanta que seu endpoint já está no ar e aceita o POST (validando a assinatura) antes de cadastrá-lo.

O ping tem o formato:

{ "id": "evt_...", "type": "webhook.ping", "createdAt": "2026-06-15T12:00:00.000Z", "data": { "message": "Verificação de saúde do endpoint (Conttrole)." } }

A mesma verificação roda ao reativar um endpoint ou ao trocar a URL de um endpoint ativo (PATCH /v1/webhooks/{id}).

Formato da entrega

Cada evento é um POST JSON no seu endpoint:

{ "id": "evt_9f3a...", "type": "document.authorized", "createdAt": "2026-06-10T12:00:00.000Z", "data": { "documentId": "ckv...", "type": "NFE", "series": 1, "number": 123, "accessKey": "3526...", "protocolNumber": "135...", "totalValue": "199.90" } }

Headers enviados:

HeaderConteúdo
X-Conttrole-EventO tipo do evento (ex: document.authorized)
X-Conttrole-DeliveryId único da entrega
X-Conttrole-Signaturet=<timestamp>,v1=<assinatura>

Validar a assinatura

A assinatura é o HMAC-SHA256 de "<timestamp>.<corpo cru>", usando o secret do endpoint. Recalcule e compare antes de confiar no payload.

import { createHmac, timingSafeEqual } from "crypto"; function verify(rawBody: string, header: string, secret: string): boolean { const parts = Object.fromEntries( header.split(",").map((kv) => kv.split("=")), ); const expected = createHmac("sha256", secret) .update(`${parts.t}.${rawBody}`) .digest("hex"); return timingSafeEqual(Buffer.from(expected), Buffer.from(parts.v1)); }

Entregas e retries

  • Respostas 2xx marcam a entrega como entregue.
  • Qualquer outra resposta (ou timeout de 10s) agenda novas tentativas com backoff exponencial (até 5 tentativas). Esgotadas, a entrega fica falha.
  • Reenvio automático: ao esgotar as tentativas imediatas, a entrega é reagendada automaticamente com atraso crescente (até ~24h), caso seu endpoint volte do ar — sem você fazer nada.
  • Reenvio manual: reenvie uma entrega específica via POST /v1/webhooks/{id}/deliveries/{deliveryId}/redeliver ou pelo botão Reenviar na tela Webhooks do painel.
  • Consulte as entregas recentes em GET /v1/webhooks/{id}/deliveries ou na tela Webhooks do painel.
  • Use o id do evento (evt_...) para deduplicar no seu lado — a mesma entrega pode chegar mais de uma vez em cenários de retry.

Desativação automática

Para não acumular entregas fadadas ao fracasso, um endpoint é desativado automaticamente (isActive: false) após 5 entregas consecutivas com falha (cada uma já tentada por até ~24h). Quando isso acontece, o campo disabledReason explica o motivo e disabledAt registra quando. Uma entrega bem-sucedida zera o contador (consecutiveFailures).

Reativar (switch on/off)

Na tela Webhooks do painel há um switch on/off por endpoint. Ao ligar, a Conttrole refaz o POST de verificação — só reativa se o endpoint responder 2xx (senão mostra o erro e mantém desativado). Via API, reative com:

curl -X PATCH https://api.conttrole.io/v1/webhooks/{id} \ -H "Authorization: Bearer ck_live_..." \ -H "Content-Type: application/json" \ -d '{ "isActive": true }'

Reativar zera o contador de falhas. Se o endpoint ainda não responde 2xx, a reativação é recusada com 422 (webhook_unreachable).

Testar

Envie um evento de teste (webhook.test) sem emitir nada:

curl -X POST https://api.conttrole.io/v1/webhooks/{id}/test \ -H "Authorization: Bearer ck_live_..."

A referência completa de todos os endpoints está em Referência da API.

Last updated on