Pular para conteúdo

Webhooks

Webhooks existem por dialeto, e só onde o provedor de origem os tem.

Dialeto Webhooks
FocusNFE Sim. Gatilhos, dois eventos aplicáveis à NFC-e
SmartNFCe Sim. Uma configuração por empresa e ambiente. Ver SmartNFCe
ACBrAPI Não existem. O provedor acompanha por consulta, e nós também

Quando nada é entregue

Comece por aqui. São três situações em que integradores esperam um aviso que deliberadamente não vem. Uma integração construída à espera dele trava sem erro nenhum.

  • Entrar em contingência não dispara evento. Um aviso de autorização é sempre uma resposta da SEFAZ, e entrar em contingência não é uma. A entrada você já conhece pelo próprio desfecho da emissão. O que acontece depois chega nos avisos documento a documento da resolução.
  • Uma transmissão sem desfecho conhecido não dispara nada. Se a SEFAZ nunca disse o que aconteceu, não há veredito a comunicar. Anunciar uma rejeição que ela não emitiu seria pior do que o silêncio. O aviso vem quando a consulta provar o desfecho.
  • Um cancelamento recusado não dispara nada. A recusa não mudou o documento: ele continua autorizado, exatamente como estava.

A regra por trás das três é a mesma, e vale para todos os dialetos: avisamos desfechos, não tentativas.

Gatilhos do FocusNFE

A emissão de NFC-e é síncrona, então não há callback de conclusão de emissão: o desfecho já veio na resposta do POST. Isso se reflete no próprio contrato do provedor, cuja lista de eventos não tem um evento nfce. Sobram dois, e são os dois que registramos:

Evento Quando dispara
nfce_contingencia Um documento emitido em contingência offline foi resolvido (entregue à SEFAZ ou fracassado)
inutilizacao A SEFAZ registrou uma inutilização efetiva

Tentar registrar qualquer outro evento responde 422.

O gatilho de nfce_contingencia dispara apenas para documentos realmente emitidos em contingência offline. Um envio comum cujo desfecho foi resolvido depois, por consulta, não dispara este gatilho. Ele nunca esteve em contingência.

O gatilho de inutilizacao dispara para toda inutilização efetiva da empresa, não só para as que passaram por este adaptador. Ele inclui as feitas pelo painel e as automáticas. Só inutilizações efetivas disparam. Recusas da SEFAZ não.

Requisitos do seu endpoint

A URL registrada precisa ser alcançável a partir da internet pública:

  • http e https. Recusamos outros esquemas no registro, com 422.
  • Sem endereços privados. Recusamos no registro os endereços de loopback, de redes privadas, link-local, CGNAT e de metadados de nuvem. A restrição continua valendo a cada envio, não só no cadastro. Um endpoint que aponte para um endereço privado no momento do envio não recebe a requisição: a tentativa apenas conta na escada de retentativas. Para testar localmente, use um túnel com endereço público.
  • Não seguimos redirecionamentos. Um 3xx conta como tentativa fracassada. Registre a URL final.
  • Cabeçalho de autenticação. authorization_header aceita letras, números e hífen. authorization aceita ASCII imprimível. Nós repassamos os dois literalmente, como cabeçalho da requisição de saída.

Registro

curl -X POST https://focusnfe.api.veraciti.com.br/v2/hooks \
  -u 'SEU_TOKEN_AQUI:' \
  -H 'Content-Type: application/json' \
  -d '{
    "event": "nfce_contingencia",
    "url": "https://seu-sistema.exemplo.com.br/veraciti/hooks",
    "authorization": "um-segredo-seu",
    "authorization_header": "X-Auth-Token"
  }'

O CNPJ é o da sua credencial. Informar um CNPJ diferente responde 403. Não aceitamos registro por cpf, porque os tokens são por empresa.

São no máximo 10 gatilhos ativos por empresa e ambiente, somando os eventos. O registro seguinte responde 422 erro_validacao pedindo que você exclua um antes.

O limite é nosso e fica num eixo diferente do que o provedor documenta. Ele permite 5 gatilhos por empresa para o mesmo evento. Nós contamos 10 no total, sem olhar o evento. Como a NFC-e tem dois eventos, os dois tetos chegam a dez.

As formas, porém, não batem. O provedor recusa um sexto gatilho num mesmo evento, e nós aceitamos até o décimo no conjunto. Dez gatilhos cobrem várias URLs de destino para cada evento.

DELETE /v2/hooks/{id} desativa o gatilho: ele para de disparar e some da listagem. O histórico de entregas continua consultável. Nós abandonamos qualquer retentativa pendente ao encontrar o gatilho inativo. A vaga volta para o limite de dez.

Autenticação da entrega

A autenticação é a do provedor, verbatim. Nós enviamos o valor que você registrou em authorization no cabeçalho nomeado por authorization_header (por padrão, Authorization). Não há assinatura HMAC. É um segredo compartilhado em cabeçalho. Trate a URL do seu endpoint como sensível e prefira HTTPS.

Retentativas

Nós repetimos uma entrega que não responder 2xx, na escada fixa do provedor: 1 minuto, 30 minutos, 1 hora, 3 horas, 24 horas. São seis tentativas no total, contando a primeira. Depois da última, nós descartamos o evento, e ele não volta.

O corpo é congelado no momento do disparo: uma retentativa reenvia o que o evento dizia, não o estado que o documento tem agora. Se o seu processamento depende do estado atual, consulte o documento ao receber o gatilho em vez de confiar no corpo.

Faça o seu recebedor idempotente

A entrega é ao menos uma vez. Uma falha nossa entre o envio e o registro do resultado repete a mesma entrega, com o mesmo corpo congelado. Isso acontece mesmo que o seu sistema já a tenha processado com sucesso. Trate o gatilho por uma chave própria (a ref do documento, a faixa da inutilização) e ignore repetições.

Formato do corpo

nfce_contingencia envia o corpo de consulta do documento (sem os campos de QR Code, que as rotas de arquivo servem sob demanda). inutilizacao envia o corpo da resposta de inutilização. Ambos estão descritos na referência do FocusNFE.