Webhooks
Webhooks permitem que a API Frota162 avise seu sistema automaticamente quando algo acontece na sua frota — sem precisar consultar a API repetidamente. Sempre que um evento ocorre, a API faz um POST para a URL cadastrada com os dados do evento em JSON.
A entrega é at-least-once: em caso de falha, o mesmo evento pode ser reenviado mais de uma vez. Trate os eventos de forma idempotente (veja Trate duplicatas).
Tipos de eventos
| Evento | ID | Descrição |
|---|---|---|
| Nova multa cadastrada | 1 | Quando uma infração é registrada |
| Atualização de multa | 2 | Quando uma infração é atualizada |
| Nova notificação cadastrada | 3 | Quando uma notificação de infração é registrada |
| Atualização de notificação | 4 | Quando uma notificação é atualizada |
| Taxa de IPVA | 5 | Quando uma taxa de IPVA é registrada |
| Taxa de DPVAT | 6 | Quando uma taxa de DPVAT é registrada |
| Taxa de licenciamento | 7 | Quando uma taxa de licenciamento é registrada |
| Cronotacógrafo | 8 | Quando um certificado de cronotacógrafo é atualizado |
| Dados de veículo novos | 9 | Quando novos dados de um veículo são consultados |
| Atualização de dados de veículo | 10 | Quando dados de veículo são atualizados |
| Status de indicação de condutor | 11 | Cada mudança de status em uma indicação de condutor — ver Indicação de Motoristas (API v2) |
Cadastrar webhook via API
Antes de montar a chamada, a URL cadastrada precisa atender aos seguintes requisitos:
- HTTPS obrigatório — URLs
http://são rejeitadas. - Host público — endereços privados, de loopback ou reservados são rejeitados (ex.:
localhost,127.0.0.1, faixas10.x,172.16–31.x,192.168.x,169.254.x, IPv6::1e faixas privadas). - Hostname resolvível — o domínio precisa resolver para um IP público válido.
Se a URL não atender a esses critérios, o cadastro do webhook é recusado.
POST /key/webhooks/add
curl -X POST \
https://apidev.v1.frota162.com.br/key/webhooks/add \
-H 'Authorization: Basic SEU_ACCESS_TOKEN' \
-H 'Key: SUA_ASSINATURA_HMAC' \
-H 'cache-control: no-cache' \
-d '[{
"url": "https://seu-sistema.com/webhooks/frota162",
"event_id": 1,
"company_id": 123
}]'
Você pode cadastrar múltiplos webhooks no mesmo request enviando um array de objetos.
Resposta de sucesso:
{
"events": [
{
"result": {
"url": "https://seu-sistema.com/webhooks/frota162",
"event_id": "1",
"client_id": "123",
"id": 456
},
"code": 201
}
],
"error": false,
"code": "fbk_200"
}
Enviar um webhook com a mesma url + event_id de um já cadastrado retorna erro fbk_008 — a entrada existente não é sobrescrita. A API não expõe rota de atualização ou exclusão de webhooks.
Estrutura dos payloads
- Multas
- Notificações
- IPVA / DPVAT / Licenciamento
- Cronotacógrafo
- Veículo
event_type: "frame"
{
"event_type": "frame",
"id": 1,
"company_id": 1,
"car": {
"car_id": 1,
"car_plate": "ABC1234"
},
"frame": {
"ait": "R1111111",
"type": "MULTA",
"at": "2024-01-11",
"time": "20:26:00",
"expiration_at": "2024-03-02",
"code": "74550",
"description": "TRANSITAR EM VELOCIDADE SUPERIOR A MAXIMA PERMITIDA EM ATE 20%",
"address": "RUA AFONSO GARBUIO, N. 790",
"city_code": "3550308",
"city": "SAO PAULO",
"state": "SP",
"points": 4,
"amount": 130.16,
"discount_amount": 104.13,
"driver_indicate": 1
},
"organization": {
"organization_code": 1,
"organization_name": "DETRAN-SP"
},
"driver": {
"id": 456,
"indicate": "2024-01-20T10:00:00.000Z",
"indicated_recieve_doc_at": "2024-01-21T10:00:00.000Z",
"indicated_sent_doc_org_at": "2024-01-22T10:00:00.000Z",
"name": "JOAO DA SILVA",
"license": "12345678900",
"identification": "123456789",
"identification_state": "SP",
"tax_id": "12345678909",
"address": "RUA EXEMPLO",
"address_number": "100",
"address_zip_code": "01000-000",
"distric": "SP",
"city": "SAO PAULO",
"state": "SP"
},
"payment": {
"paid": true,
"at": "2024-02-01",
"amount": 104.13
},
"link": "https://boleto.example.com/abc123",
"sne_boleto_status": "PAGO",
"created_at": "2024-04-05T20:49:18.000Z",
"updated_at": "2024-04-06T09:00:00.000Z"
}
O campo driver_indicate indica se o condutor já foi identificado: 0 = não indicado, 1 = indicado. Os campos de driver (dados do condutor, CNH, CPF, endereço) são preenchidos quando driver_indicate for 1. O objeto frame traz também city_code (código IBGE da cidade), e no nível raiz link (boleto) e sne_boleto_status (status do boleto no SNE).
Objeto payment
O bloco payment descreve a situação de pagamento da multa:
| Campo | Tipo | Descrição |
|---|---|---|
paid | boolean | Indica se a multa consta como paga. |
at | string | null | Data do pagamento no formato YYYY-MM-DD. null quando não há data registrada. |
amount | number | Valor pago. 0 quando não há valor registrado. |
paid pode ser true com at: null e amount: 0Nem sempre a data e o valor do pagamento estão disponíveis: paid pode vir true com at em null e amount em 0. Use paid como fonte de verdade para saber se a multa foi paga; não infira o pagamento a partir de at/amount.
event_type: "notification"
{
"event_type": "notification",
"id": 1,
"company_id": 1,
"car": {
"car_id": 1,
"car_plate": "ABC1234"
},
"notification": {
"ait": "N1234567",
"at": "2024-01-11",
"time": "20:26:00",
"indication_limit_at": "2024-02-11",
"code": "74550",
"description": "TRANSITAR EM VELOCIDADE SUPERIOR A MAXIMA PERMITIDA",
"address": "RUA EXEMPLO, 100",
"city_code": "3550308",
"city": "SAO PAULO",
"state": "SP",
"amount": 130.16,
"discount_amount": 104.13,
"driver_indicate": 1,
"points": 4
},
"organization": {
"organization_code": 1,
"organization_name": "DETRAN-SP"
},
"driver": {
"id": 456,
"indicate": "2024-01-20T10:00:00.000Z",
"indicated_recieve_doc_at": "2024-01-21T10:00:00.000Z",
"indicated_sent_doc_org_at": "2024-01-22T10:00:00.000Z",
"name": "JOAO DA SILVA",
"license": "12345678900",
"identification": "123456789",
"identification_state": "SP",
"tax_id": "12345678909",
"address": "RUA EXEMPLO",
"address_number": "100",
"address_zip_code": "01000-000",
"distric": "SP",
"city": "SAO PAULO",
"state": "SP"
},
"link": "https://boleto.example.com/abc123",
"linkNotification": "https://notificacao.example.com/abc123",
"sne_boleto_status": "PENDENTE",
"created_at": "2024-04-05T20:49:18.000Z",
"updated_at": "2024-04-06T09:00:00.000Z"
}
Os campos seguem o mesmo padrão de Multas. Exclusivos de notificação: indication_limit_at (prazo-limite para indicar o condutor) e linkNotification (link da notificação, além do link do boleto).
event_type: "DEBITOS-IPVA" / "DEBITOS-DPVAT" / "DEBITOS-LICENCIAMENTO"
O mesmo formato se aplica aos três — o event_type muda conforme o tributo.
{
"event_type": "DEBITOS-IPVA",
"id": 1,
"company_id": 1,
"car": {
"car_id": 1,
"car_plate": "ABC1234"
},
"ammount": 1250.00,
"exercise": "2024",
"occurrence": "01",
"expedition_at": "2024-01-31",
"quote": 1,
"created_at": "2024-01-15T10:00:00.000Z",
"updated_at": null
}
ammount é o valor do tributo, exercise o ano-exercício e quote a cota/parcela.
DEBITOS-Os event_type de débito (DEBITOS-IPVA, DEBITOS-DPVAT, DEBITOS-LICENCIAMENTO) são os únicos que vem em UPPERCASE com o prefixo DEBITOS-. Todos os demais eventos usam event_type em lowercase (frame, notification, cronotacografo, car, driver_indication).
A comparação no seu handler deve ser exata — não aplique toLowerCase() nem qualquer normalização de case antes do match. Se normalizar, DEBITOS-IPVA vira debitos-ipva e nunca vai bater.
Comportamento de created_at / updated_at
Eventos de débito são disparados apenas na criação do registro — não há disparo em atualização. Por isso, updated_at sempre chega como null no payload.
| Campo | Valor no payload | Motivo |
|---|---|---|
created_at | timestamp da criação | O webhook só dispara quando o débito é registrado pela primeira vez |
updated_at | null | Atualizações posteriores do débito não geram webhook |
Como o webhook de débito só dispara na criação, todo payload recebido representa um novo débito — não é necessário diferenciar criação de atualização. Trate o evento como inserção.
Escopo dos tributos com webhook
Apenas os três tributos abaixo geram eventos de webhook:
event_type | Tributo |
|---|---|
DEBITOS-IPVA | IPVA |
DEBITOS-DPVAT | DPVAT |
DEBITOS-LICENCIAMENTO | Licenciamento |
Outros tipos de débito (DETRAN, DER, DERSA, CETESB, RENAINF, municipais, polícia rodoviária) são registrados no sistema, mas não geram webhook — nenhum evento é disparado para esses tributos.
event_type: "cronotacografo"
{
"event_type": "cronotacografo",
"id": 1,
"company_id": 1,
"car": {
"id": 1,
"rim": "22.5",
"tire": "295/80",
"renavam": "00123456789",
"plate": "ABC1234",
"chassi": "9BWZZZ377VT004251"
},
"gru": {
"number": "00190000090123456789",
"ammount": "150.00",
"payment_at": "2024-01-10T14:00:00.000Z"
},
"result": {
"issue_at": "2024-01-01T00:00:00.000Z",
"expiration_at": "2025-01-01T00:00:00.000Z",
"document": "CERTIFICADO",
"document_number": "123456",
"responsible": "FULANO DE TAL"
},
"link": "https://link-do-certificado.pdf",
"sealing": {
"at": "2024-01-01T00:00:00.000Z",
"state": "SP",
"serie": "ABC123",
"brand": "VDO",
"model": "1381"
},
"rehearsal": {
"state": "SP",
"point": "POSTO EXEMPLO",
"at": "2024-01-01T00:00:00.000Z",
"valid": "2025-01-01T00:00:00.000Z",
"updated": "2024-01-01T00:00:00.000Z",
"standard": "PADRAO",
"read_at": "2024-01-01T00:00:00.000Z"
},
"created_at": "2024-01-15T10:00:00.000Z",
"updated_at": null
}
event_type: "car"
{
"event_type": "car",
"id": 1,
"company_id": 1,
"plate": "ABC1234",
"renavam": "00123456789",
"kind": "AUTOMÓVEL",
"chassi": "9BWZZZ377VT004251",
"state": "SP",
"type": "PASSEIO",
"branding": "TOYOTA",
"model": "COROLLA",
"manufactoryYear": "2023",
"color": "BRANCO",
"result": {
"success": true,
"message": "OK"
}
}
Indicação de condutor (event_type: "driver_indication") — API v2
Disparado a cada mudança de status de uma indicação de condutor. Consulte a lista completa de status no módulo de Indicação de Motoristas.
{
"id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"driver_id": 12345,
"company_id": 789,
"event_type": "driver_indication",
"status": "CONFIRMED",
"can_reindicate": false,
"vehicle_type": "CAR",
"signer_type": "OWNER",
"notification_id": "b2c3d4e5-f6a7-8901-bcde-f23456789012",
"created_at": "2026-05-14T10:00:00.000Z",
"updated_at": "2026-05-14T10:30:00.000Z"
}
wrong_documentsQuando status for wrong_documents, o payload inclui o campo adicional "can_reindicate": true, indicando que a indicação pode ser corrigida e reenviada.
Segurança dos webhooks
Cada requisição de webhook inclui os mesmos headers de autenticação HMAC usados nas chamadas da API:
Authorization: Basic {SEU_ACCESS_TOKEN}
Key: {ASSINATURA_HMAC}
Content-Type: application/json
Valide esses headers no seu servidor para garantir que o webhook veio da Frota162. O código de validação está na seção Boas práticas abaixo.
IPs de origem
Os webhooks são enviados a partir dos seguintes IPs:
20.84.24.3
18.234.9.54
35.231.115.63
34.227.129.114
Configure seu firewall para aceitar requisições desses IPs caso use allowlisting de IPs no seu servidor.
Boas práticas no recebimento
Responda rapidamente
Seu endpoint deve responder com HTTP 200 em menos de 5 segundos. Se o processamento for demorado, salve o payload em fila e processe de forma assíncrona.
app.post('/webhooks/frota162', async (req, res) => {
// Responda imediatamente
res.status(200).send('OK');
// Processe de forma assíncrona
await fila.adicionar(req.body);
});
Valide a autenticação
const crypto = require('crypto');
app.post('/webhooks/frota162', (req, res) => {
const keyHeader = req.headers['key'];
const assinaturaEsperada = crypto
.createHmac('sha256', process.env.FROTA_SECRET_KEY)
.update(process.env.FROTA_ACCESS_TOKEN)
.digest('hex');
if (keyHeader !== assinaturaEsperada) {
return res.status(401).send('Não autorizado');
}
res.status(200).send('OK');
});
Trate duplicatas
A Frota162 pode reenviar o mesmo webhook em caso de falha. Use o id do evento para detectar e ignorar duplicatas.
const eventosProcessados = new Set();
app.post('/webhooks/frota162', async (req, res) => {
const { id, event_type } = req.body;
const chave = `${event_type}_${id}`;
if (eventosProcessados.has(chave)) {
return res.status(200).send('Já processado');
}
eventosProcessados.add(chave);
// ... processar evento
res.status(200).send('OK');
});
Testar o recebimento
Depois de cadastrar o webhook e preparar seu endpoint, você pode disparar um evento de teste diretamente pelo sistema Frota162 — sem esperar um evento real acontecer e sem precisar abrir chamado no suporte. O disparo envia um payload com dados fictícios do tipo de evento configurado, ideal para validar a conexão e a autenticação do seu endpoint.
Passo a passo
- Acesse o perfil da empresa no sistema Frota162.
- Role a página até a seção Webhooks.
- Localize o webhook cadastrado. Ao lado do botão Logs, clique em Testar webhook.
- O sistema dispara um evento com dados fictícios correspondentes ao tipo de evento configurado naquele webhook.
- Confira no seu endpoint se o
POSTchegou — com os headersAuthorizationeKey(veja Segurança dos webhooks) e o corpo no formato esperado (veja Estrutura dos payloads).
O disparo de teste serve apenas para validação de conexão. Os dados enviados são fictícios e não correspondem a multas, notificações ou veículos reais.
Se o teste não chegar, verifique os erros de entrega em Monitorar e reenviar webhooks e confirme que sua URL aceita POST com content-type JSON e responde rapidamente (veja Responda rapidamente).
Monitorar e reenviar webhooks
Quando seu servidor retorna erro ou não responde dentro do limite de tempo, a entrega falha e fica registrada no log de erros. Use os endpoints abaixo para inspecionar falhas e reprocessá-las sem precisar aguardar que o evento ocorra novamente.
Listar erros de entrega
Retorna os webhooks que não foram entregues com sucesso. Cada entrada inclui o id do log de erro (necessário para reenvio), a URL de destino, o payload que falhou e o código de resposta recebido (ou o motivo do timeout).
GET /key/webhooks-errors?pagination[page]=1&pagination[perpage]=50
curl -X GET \
'https://apidev.v1.frota162.com.br/key/webhooks-errors?pagination[page]=1&pagination[perpage]=50' \
-H 'Authorization: Basic SEU_ACCESS_TOKEN' \
-H 'Key: SUA_ASSINATURA_HMAC' \
-H 'cache-control: no-cache'
O parâmetro
pagination[perpage]aceita no máximo 100 itens por página. Valores acima de 100 são limitados a 100.
Reenviar um webhook com erro
Reprocessa uma entrega específica usando o id retornado pelo endpoint de listagem acima.
POST /key/webhooks/logs/{evento_id}/resend
curl -X POST \
https://apidev.v1.frota162.com.br/key/webhooks/logs/123/resend \
-H 'Authorization: Basic SEU_ACCESS_TOKEN' \
-H 'Key: SUA_ASSINATURA_HMAC' \
-H 'cache-control: no-cache'
Substitua
123peloiddo log de erro obtido na listagem acima.
Próximos passos
| Quero... | Ir para... |
|---|---|
| Entender os códigos de erro da API | Tratamento de Erros |
| Ver o guia completo de integração | Introdução |