SigMe API - Guia Técnico para Clientes e Integradores
Objetivo
Este documento apresenta a base técnica da SigMe API para empresas que irão consumir, integrar, distribuir ou operar soluções sobre a plataforma.
O foco é o contrato público de integração:
- autenticação e autorização
- isolamento multiempresa
- catálogos e payloads estáveis
- padrões de requisição e resposta
- canais HTTP e WebSocket publicados pela API
- considerações operacionais para ambientes corporativos
Este documento não substitui a especificação OpenAPI. Use-o como visão técnica de onboarding; use o OpenAPI como referência de endpoints, parâmetros e schemas.
Visão Geral da Plataforma
A SigMe API é uma API REST/JSON para monitoramento, gestão de ativos, usuários, empresas, dispositivos, instalações e atualizações em tempo real.
Características relevantes para integração:
- API REST com payloads JSON
- documentação OpenAPI/Swagger publicada pela própria aplicação
- autenticação por JWT Bearer e por API Key
- validação de payloads na entrada da API
- isolamento multiempresa por empresa autenticada
- telemetria e posição disponíveis via endpoints HTTP e WebSocket documentados
O contrato público de integração é a API HTTP/WebSocket e seus payloads. Processamentos assíncronos, quando existirem, continuam encapsulados por esses endpoints e estados retornados.
Ambientes e Exposição
Ambientes e rotas públicas:
- ambiente local:
http://localhost:3000 - ambiente produtivo:
https://api.knsh.com.br - portal de documentação:
/ - Swagger UI:
/swagger - OpenAPI JSON:
/swagger/json - guia técnico HTML:
/docs/guide - guia técnico Markdown:
/docs/guide.md
Recomendações de onboarding:
- comece pelo portal de documentação
- descubra endpoints e schemas pelo OpenAPI
- use o Swagger UI para autenticação manual e testes exploratórios
- use este guia para alinhar autenticação, tenancy e operação
Autenticação e Autorização
Mecanismos de Autenticação
A plataforma aceita dois mecanismos de autenticação:
| Mecanismo | Header | Caso de uso |
|---|---|---|
| JWT Bearer | Authorization: Bearer <token> | Usuários autenticados via portal ou app |
| API Key | X-Api-Key: <chave> | Integrações server-to-server sem sessão |
Regras de precedência:
- Se
Authorization: Bearerestiver presente, a autenticação é JWT. Token inválido retorna401imediatamente, sem tentar API Key. - Se apenas
X-Api-Keyestiver presente, a autenticação é por API Key. - Se nenhum dos dois estiver presente, a API retorna
401 Unauthorized. - Endpoints públicos não exigem autenticação.
Autenticação JWT
Formato esperado:
Authorization: Bearer <jwt>
Fluxos públicos:
POST /auth/register— cria usuário e credencial de autenticação, vinculando à empresa informada (companyID,roleID,typeID)POST /auth/loginPOST /auth/forgot-passwordPOST /auth/reset-password
Fluxos autenticados:
PATCH /auth/passwordGET /auth/refresh-token
Autorização
A autorização usa o papel e as permissões do usuário autenticado.
Conceitos relevantes:
- usuários de empresa operam apenas no escopo da própria empresa
- permissões são organizadas por módulo e ação (leitura, criação, atualização, exclusão e ações específicas)
- autenticação por API Key identifica a empresa e restringe o acesso aos dados dela, sem papéis ou permissões granulares de usuário
Formato de permissions no contexto autenticado:
- mapa por módulo com arrays de ações permitidas
- exemplo:
{"company": ["read", "update"], "user": ["read"], "color": ["read"]}
Autenticação válida não implica acesso global. O token define o escopo e as permissões efetivas da operação.
Autenticação por API Key para Integrações
Integrações server-to-server podem autenticar apenas com X-Api-Key, sem login, JWT ou refresh.
Como funciona
X-Api-Key: sigme_<chave_da_empresa>
- A chave identifica a empresa e restringe o acesso aos dados dela
- Não é necessário enviar
Authorization: Bearer - A chave plana é exibida apenas no momento da geração; depois disso não é recuperável
- A plataforma não armazena a chave em texto plano
Verificar conectividade
GET /integration/me
X-Api-Key: sigme_<chave>
Resposta 200:
{ "companyId": 7, "companyName": "Transportadora Exemplo Ltda" }
Use esse endpoint no startup da integração para validar a configuração.
Endpoints acessíveis via API Key
A API Key cobre monitoramento e integração. Endpoints de gestão (usuários, veículos, dispositivos etc.) exigem JWT com permissões.
| Endpoint | Descrição |
|---|---|
GET /integration/me | Verificar conectividade e obter dados da empresa |
GET /integration/events | Listar alertas operacionais da empresa (paginado; sinceId para polling incremental) |
GET /integration/event-types | Catálogo de tipos de alerta |
GET /integration/devices/:deviceId/trail | Histórico de posições de um dispositivo pelo ID externo |
GET /map/positions | Visão geral das posições dos veículos |
GET /map/vehicles/:vehicleId | Posição detalhada e trilha histórica do veículo |
WebSocket /location-stream | Atualização de posição em tempo real |
Tentativas de acessar endpoints de gestão com API Key retornam 403 Forbidden.
Escopo da API Key
Com API Key, a integração opera no escopo da empresa identificada pela chave. Operações que dependem de usuário, papel ou permissões granulares exigem JWT.
Segurança e boas práticas
- Nunca expor a API Key em frontend ou repositório público
- Armazenar em variáveis de ambiente ou gerenciadores de secrets
- Rotacionar periodicamente em produção
- Em caso de comprometimento, revogar e regenerar pelo painel administrativo
Modelo Multiempresa
A SigMe API é multi-tenant.
Regras relevantes:
- empresas clientes acessam apenas os próprios recursos
- recursos administrativos globais permanecem restritos a contextos com permissão apropriada
- clientes não devem inferir ou forçar escopo apenas por IDs enviados no request
- a API é a fonte de verdade para escopo, posse e autorização
Consequência prática:
- desenhe integrações com segregação rígida de dados por empresa
- listagens, detalhes, atualizações e eventos devem respeitar o tenant do token utilizado
Padrões de Payload e Validação
A API valida e normaliza campos na entrada. Isso importa porque valores como documento, email e telefone podem ser persistidos em formato canônico.
Exemplos estabilizados:
- CPF, CNPJ, email e telefone são normalizados
- CEP e UF são normalizados nos contratos de endereço
- em criações,
statusIDpode ser omitido quando o recurso nasce ativo por padrão - o documento da empresa é persistido em formato canônico
Recomendações:
- envie dados semanticamente corretos, mesmo quando a API normalize parte do conteúdo
- não dependa de comportamentos não documentados fora do OpenAPI e deste guia
Convenção de Timestamps
Para datas e horas serializadas pela API:
- timezone padrão:
America/Sao_Paulo - formato de saída: ISO 8601 com offset explícito
- exemplo:
2026-04-07T12:35:00.000-03:00
Entrada (startDate / endDate em query)
- com offset ou
Z→ instante absoluto (2026-07-24T16:41:00.000Z,2026-07-24T13:41:00.000-03:00) - sem timezone (ex.:
2026-07-24T13:41) → horário de parede emAmerica/Sao_Paulo - clientes web no Brasil podem enviar o valor do input local sem converter para UTC
Implicações:
- não assumir saída em UTC com sufixo
Z - interpretar sempre o offset retornado pela API
- evitar parsing baseado em substring fixa de timezone
Quando um campo temporal estiver presente em payloads de leitura operacional, trate-o como horário já formatado no timezone padrão da API, salvo documentação específica em contrário.
Catálogos e Contratos Canônicos
Alguns catálogos operacionais devem ser tratados como contratos estáveis.
StatusType
Semântica canônica de status-type:
1 = active2 = inactive3 = pending
Implicações:
- integrações podem tratar esses estados como catálogo conhecido
- a API continua sendo a fonte oficial para leitura do catálogo
UserRole
Papéis canônicos de sistema: principal_admin, admin e user. Também existem papéis custom por organização.
Modelo de autorização:
- o JWT carrega
organizationID,organizationType(OWNER\|TRACKING\|CLIENT),membershipID,isPrincipalAdminescopeOrganizationIds - TRACKING pode filtrar leituras operacionais com
organizationIDexclusivo (um cliente directory por vez; default = frota da home; nunca mistura). Quando o cliente é selecionado,driveré omitido. Relatório de atividade de usuários não aceita este filtro OWNERopera catálogos/plataforma; não lista automaticamente veículos, motoristas ou mapa de tenants- papéis de sistema são globais; o template de
admin/usersó pode ser alterado pelo operador da plataforma (OWNER) - papéis custom pertencem a uma organização;
admin/principal_adminda organização podem criar, renomear, editar o template e remover quando não estiver em uso - o template custom é limitado ao teto do
principal_admindo tipo da org (TRACKINGouCLIENT); grants acima desse teto são descartados na gravação - nomes
principal_admin/admin/usersão reservados (masternão é mais emitido) - permissões efetivas do usuário ficam no vínculo (membership);
permissionsOverride=trueindica override manual principal_adminrecebe o template do tipo da org no JWT (não o catálogo completo); o acesso a registros continua limitado ao escopo resolvido- alterações de permissão passam a valer no JWT após novo login ou refresh
GET /permissions/catalogdevolvemodules,actions,required(conjunto base:auth.login,device.read,self.reade reads silenciosos de catálogo:manufacturer,device-type,status-type,user-type,color,default-command) eceiling(mapa máximo concedível). OWNER vê o catálogo completo; TRACKING/CLIENT vêem só o teto doprincipal_admin(sem módulos de catálogo na matriz). Grants base devem ser tratados como travados em UIs de gestão. Tokens/cargos antigos comhistorysão expandidos paratracking-report:reportespeeding-report:report- o módulo
eventautoriza a listagem de eventos (GET /event);notificationscobre push e histórico de notificações
Endpoints relevantes:
| Método | Caminho | Descrição |
|---|---|---|
GET | /permissions/catalog | Vocabulário concedível (modules, actions, required, ceiling) |
GET | /user-role | Lista papéis no escopo do autenticado |
POST | /user-role | Cria papel custom com template |
PUT | /user-role/:id/permissions | Atualiza template (propagate opcional) |
PATCH | /user-company-register/:id/permissions | Override ou reset para o template da role |
PUT | /default-permissions/:roleName | Template de papel de sistema (somente master) |
Implicações:
- trate os papéis canônicos como catálogo estável
- a autorização efetiva continua dependente do token e das permissões emitidas
- em gestão de acesso, prefira
roleIDe/user-role/:id/permissions
UserType
O catálogo user-type classifica usuários operacionalmente e deve ser consumido pela API como fonte de verdade.
Implicações:
- trate esses tipos como catálogo estável
- sincronize pela API quando precisar de cópia local explícita
Superfícies Públicas Principais
Principais áreas da superfície pública:
auth: autenticação JWT, refresh e escopo do usuário autenticadointegration: conectividade e autenticação server-to-server via API Keycompany: gestão empresarialuser: identidade e gestão de usuários por empresaaddress: endereço com normalização de CEP e UFstatus-type,user-roleeuser-type: catálogos operacionaispreferences(preferências de notificação do usuário),parameters(parâmetros do sistema por empresa),default-permissionsepermissions/catalog: preferências/eventos e vocabulário/templates de permissãoactivation-key: geração, consulta e consumo de chaves operacionaisdevice: cadastro de dispositivos e leitura operacional de telemetriadevice-company-registerefcm-token: vínculos empresa/dispositivo e notificação pushsim-card: inventário de chips por empresa e vínculo opcional a dispositivosvehicle: veículos e catálogos de marca, modelo e tipovehicle-group: grupos/frotas de veículos por empresa (ex.: Frota A, Frota B)geofence: cercas virtuais (polígono ou círculo) com vínculos a empresa, veículos ou gruposevent,notificationecommand: leitura operacional, envio e históricouser-activity: auditoria de ações autenticadasGET /user-activityaceita ordenação opcional viasortBy(createdAt|action|module|method|endpoint|statusCode|ipAddress|user) esortDir(asc|desc); defaultcreatedAt descoverview: visão consolidada da home operacionalmap: posições, detalhe de ativos e trilhadriver: motoristas, CNH, escala de trabalho e vínculo com veículosinstallation: vínculo dispositivo ↔ veículo e catálogo de tipos de instalaçãospeeding-report: análise de velocidade da trajetória contra limites de via
Consulte sempre o OpenAPI para a lista completa e atualizada de endpoints.
Driver
O módulo driver gerencia motoristas como um tipo especializado de usuário (typeID=3),
com dados de CNH, exames periódicos, escala semanal, atribuição de veículos e identificação RFID.
Segregação User/Driver:
GET /usernão retorna motoristas (filtratypeID !== 3)GET /driverretorna apenas motoristas (typeID === 3)- Motoristas são criados exclusivamente via
POST /driver, não via/user
Vínculo de motoristas à empresa (gestão de cadastro):
Motoristas são vinculados a uma empresa no momento da criação (POST /driver).
Para vincular/desvincular motoristas existentes a uma empresa, a plataforma expõe:
GET /company/:id/drivers— lista os vínculos ativos de motoristas da empresa (dados do usuário, CNH, exames e veículos)POST /company/:id/drivers—{ "userID": 12 }cria/reativa o vínculo (typeID=3, role padrão, sem permissões e semAuth)DELETE /company/:id/drivers/:userID— inativa o vínculo do motorista na empresa
Esses endpoints preservam o modelo do motorista: sem modelo de permissões, sem credenciais
de acesso e sem inativar vínculos do mesmo motorista em outras empresas.
Listagens com contadores:
GET /companyretorna em_countos totais dedeviceRegisters,users(vínculos ativos) evehicles(vínculos ativos)GET /driverretornadriverExams(por vínculo) evehicles(vínculos ativos) para montar status de validade de exames e contagem de veículosGET /vehicleretornaregistersativos com ouser(nome) quando o vínculo pertence a um motorista
Vínculo duplo (admin + motorista):
Uma mesma pessoa pode ter dois vínculos na mesma empresa:
um como usuário administrativo e outro como motorista.
A API trata isso como dois registros UserCompanyRegister distintos
(@@unique([userID, companyID, typeID])).
Motorista não tem acesso à plataforma:
O registro de motorista não cria credenciais de autenticação (Auth).
O e-mail é opcional para motoristas.
CNH (DriverLicense):
| Campo | Descrição |
|---|---|
licenseNumber | Número da CNH (único) |
category | Categoria: A, B, AB, C, D, E |
firstLicenseDate | Data da primeira habilitação |
expirationDate | Data de validade |
observations | Observações (opcional) |
Escala de trabalho (DriverSchedule):
Escala semanal recorrente com dias da semana (0=Dom, 6=Sáb) e horários.
Exames periódicos (DriverExam):
Cada motorista possui registro de exames periódicos vinculados ao seu cadastro na empresa.
Os tipos de exame disponíveis são configurados por empresa via GET/PATCH /parameters
(chave exams). Os exames padrão são:
| Tipo | Descrição |
|---|---|
toxicology | Toxicológico |
occupational_clinical_exam | Exame Clínico Ocupacional |
visual_acuity | Acuidade Visual |
tonal_audiometry | Audiometria Tonal |
blood_count | Hemograma |
Cada registro possui examType, lastExamDate (data do último exame) e observations opcional.
Os exames são armazenados como array em driverExams no detalhe do motorista.
Validade dos exames:
A validade de cada exame é configurada por empresa nos parâmetros do sistema
(GET/PATCH /parameters, chave exams) em dias, contada a partir de lastExamDate.
Cada item de exams possui type, enabled e validityDays (opcional; quando ausente,
é usado o padrão do tipo). Padrões:
| Tipo | Validade padrão (dias) |
|---|---|
toxicology | 900 |
occupational_clinical_exam | 365 |
visual_acuity | 365 |
tonal_audiometry | 365 |
blood_count | 365 |
Exemplo de PATCH /parameters:
{
"exams": [
{ "type": "toxicology", "enabled": true, "validityDays": 900 },
{ "type": "blood_count", "enabled": false }
]
}
Quando enabled é false, o exame não é monitorado no status da tabela de motoristas.
Um exame é considerado vencido quando lastExamDate + validityDays é anterior à data atual.
Vínculo com veículos (VehicleRegister):
Motoristas podem ser vinculados a múltiplos veículos e vice-versa.
Cada vínculo possui:
| Campo | Descrição |
|---|---|
startDate | Data de início do vínculo (padrão: agora) |
endDate | Data de encerramento real (null = ativo) |
plannedEndDate | Data prevista de expiração (opcional) |
statusID | Status do vínculo |
Quando plannedEndDate é informado, o sistema notifica os administradores
da empresa nos thresholds de 30, 15, 7 e 1 dias antes do vencimento.
O tipo de notificação é driver_assignment_expiry (categoria system).
RFID do motorista:
Cada motorista pode ter um rfidCardId cadastrado por empresa (campo em UserCompanyRegister).
O ID do cartão RFID é utilizado para validar o login do motorista em campo.
O endpoint de validação GET /driver/rfid-validation compara o iddrv
recebido nos pacotes de telemetria com o RFID cadastrado para o motorista
atribuído ao veículo do dispositivo.
Alertas de vencimento da CNH:
Um job diário (08:00) verifica CNHs com vencimento em 30, 15, 7 e 1 dias
e notifica os administradores da empresa via push (FCM).
O tipo de notificação é driver_license_expiry (categoria system).
Endpoints principais:
| Método | Rota | Descrição |
|---|---|---|
POST | /driver | Criar motorista (typeID=3 fixo, sem Auth) |
GET | /driver | Listar motoristas (paginado, tenant) |
GET | /driver/:id | Detalhes do motorista (CNH, escala, exames, veículos) |
PATCH | /driver/:id | Atualizar dados básicos |
POST | /driver/:id/license | Criar CNH |
PATCH | /driver/:id/license | Atualizar CNH |
POST | /driver/:id/license/delete | Excluir CNH |
GET | /driver/:id/schedule | Buscar escala |
PUT | /driver/:id/schedule | Substituir escala (batch) |
GET | /driver/:id/exams | Listar exames periódicos |
PUT | /driver/:id/exams | Atualizar exames (batch upsert) |
GET | /driver/:id/vehicles | Veículos do motorista (inclui plannedEndDate) |
POST | /driver/:id/assign-vehicle | Vincular veículo (endDate opcional = prazo) |
POST | /driver/:id/unassign-vehicle/:vehicleRegisterID | Desvincular veículo |
GET | /driver/:id/rfid | Consultar RFID card ID |
PATCH | /driver/:id/rfid | Atualizar RFID card ID |
GET | /driver/rfid-validation?deviceId=&iddrv= | Validar correspondência RFID × motorista |
A CNH (driverLicenses), escala (driverSchedules) e exames (driverExams)
são retornadas embutidas no payload de GET /driver/:id. Os veículos (vehicles)
incluem plannedEndDate quando definido.
Validação RFID:
GET /driver/rfid-validation?deviceId={deviceId}&iddrv={iddrv}
Retorna:
{
"matched": true,
"driver": { "id": 1, "name": "João" },
"assignedDriver": { "id": 1, "name": "João" }
}
matched:truese oiddrvcoincide com orfidCardIdde um motorista atribuído ao veículodriver: motorista identificado pelo RFID (null se não houver match)assignedDriver: primeiro motorista atribuído ao veículo (para referência, mesmo sem match)
O fluxo de resolução é: deviceId → Installation → Vehicle → VehicleRegister (ativo) → UserCompanyRegister.rfidCardId.
Overview Operacional
O módulo overview expõe a visão consolidada da home operacional.
Pontos relevantes:
- o endpoint aceita período explícito para telemetria agregada
- TRACKING pode passar
organizationIDde um cliente directory (escopo exclusivo, nunca mistura com a home) - campos temporais públicos seguem a convenção de timestamp da API (
America/Sao_Paulo) generatedAt,period.startDate,period.endDatee campos comohappenedAtsão ISO 8601 com offset- a timeline e a distribuição de tipos de pacote do período representam contagem de registros válidos no intervalo consultado
- indicadores de snapshot representam o estado mais recente conhecido dos dispositivos, separados da leitura histórica do período
Processamento Assíncrono
Alguns fluxos, como comandos, notificações e exportações, podem concluir de forma assíncrona.
Para o integrador:
- acompanhe o resultado pelos endpoints e estados públicos da API
- use o status/histórico documentados no OpenAPI
Dispositivos
O módulo device cobre o cadastro de dispositivos e leituras operacionais de telemetria.
Pontos relevantes:
- a listagem de dispositivos respeita o escopo da empresa autenticada
- TRACKING lista devices da home por padrão;
organizationIDde um cliente directory substitui o escopo emGET /device(nunca mistura). Chips SIM continuam só da home GET /deviceeGET /device/by-id/:idincluempacketDatacom última telemetria processada (GPS, sinal, bateria eisOnline)- limiares de online: tracker 5 min; demais tipos 30 min
- criação e atualização de vínculo com empresa validam a permissão sobre a empresa informada; TRACKING pode atribuir à home ou a uma filha directory
PATCH /device/:idcom troca decompanyIDePOSTassign/unassign encerram a instalação ativa (Installation.endedAt+ status inactive)- dispositivos desconhecidos são emissores detectados na telemetria que ainda não possuem cadastro correspondente
- identificadores externos de dispositivo são tratados como case-insensitive na leitura operacional
GET /device/last-positions(últimas posições conhecidas) eGET /device/unknown(emissores sem cadastro) são leituras voltadas a consumidores de telemetria (permissãoconsumer:read)
Rotas, trilhas e relatórios
GET /device/tracking-reportretorna pacotes de telemetria para diagnóstico; exige permissãotracking-report:report- aceita
organizationIDexclusivo (TRACKING);driveré omitido quando o cliente é selecionado - mescla violações de cerca virtual (
GeofenceViolationLog) como pontos sintéticospacketTypeCode: 200/GEOFENCE_VIOLATIONe201/GEOFENCE_SPEED_LIMIT(badge) - quando há pacote routine do mesmo
deviceIdna janela de ±2s, a violação substitui esse pacote e herda timestamp, coords, speed e demais campos do pacote de referência (incluindo o quepacket-detailsprecisa); sem routine, ainda herda telemetria do pacote mais próximo na janela sem remover outros highlights - se o cliente filtrar
packetTypes, a API ainda carrega os pacotes de referência para o merge e só então aplica o filtro no resultado (para200/201não perder velocidade) - filtro
packetTypes: se vazio, inclui pacotes + violações; se preenchido, violações só quando200ou201estiverem na lista - informe exatamente um de
deviceId(id externo) ouvehicleId - com
vehicleId, cada pacote é recortado à vigência[createdAt, endedAt)das instalações daquele veículo (histórico de um device após a troca não permanece no veículo antigo) - paginação via
page/limit, ouall=truepara o período completo - ordenação opcional via
sortBy(timestamp|deviceId|lat|lng|speed|moving|packetType) esortDir(asc|desc); defaulttimestamp asc - filtro opcional
packetTypescom códigos de tipo de pacote separados por vírgula (catálogo 0–34 + servidor 200–255, ex.:packetTypes=3,4,200); omitido = todos os tipos - cada linha traz campos resumidos (
timestamp, coords,speed,moving,packetType),dataSummaryedatacompleto lightweight=true(defaultfalse) omitedataSummaryedatada resposta — use para tabelas/mapas de relatório e busque o pacote individual viaGET /device/packet-detailssob demanda- cada linha inclui
driver(motorista vinculado ao veículo na data/hora do pacote, conforme o período do vínculo emVehicleRegister);nullquando não há veículo/motorista identificado no instante movingsegue a mesma regra do mapa:commomdt.movdt > 0ouspdgps > 0(km/h) — alguns firmwares deixammovdtem 0 mesmo em movimentoGET /device/packet-detailsretorna o pacote bruto completo (data) de umdeviceId+timestampespecífico (chave primária dedevice_packets); exigetracking-report:reportouspeeding-report:report- parâmetros:
deviceId(id externo) etimestamp(ISO 8601, o mesmo valor devolvido nas linhas detracking-report/speeding-report) - retorna 404 se o dispositivo não pertencer à empresa do usuário (MASTER tem escopo global) ou se não houver pacote exatamente nesse instante
- pensado para modais de detalhe de rota: buscar sob demanda ao clicar num marcador, em vez de embutir o pacote completo em cada linha da listagem
- violações de cerca (
packetTypeCode: 200/201) mescladas com replace+inherit usam odeviceId/timestampdo pacote de telemetria que gerou o evento —packet-detailsresolve esse pacote de referência normalmente GET /device/route/:deviceIdaceitacleanStops(defaulttrue) para reduzir oscilação GPS enquanto o ativo está paradovehicleIdopcional recorta a rota às janelas de instalação[createdAt, endedAt)daquele veículo para o dispositivo; omitido = linha do tempo completa do device- mescla violações de cerca (
GeofenceViolationLog) no período com a mesma regra de substituição do pacote routine + herança de velocidade GET /map/vehicles/:vehicleIdaceitacleanStops(defaulttrue) na trilha retornadaGET /map/vehicles/:vehicleIdaceitastartDate/endDatepara delimitar a janela de telemetria da trilha (e da cadeia de instalações)- quando informados, a janela explícita prevalece sobre o default de 24h / lookback de
sinceIgnition - a resposta inclui
trips[]com trajetos IGN. ON → IGN. OFF na janela (startedAt,endedAtounull,open); OFF órfão é ignorado; ON sem OFF gera trajeto aberto (endedAt: null) - a trilha continua limitada por
trailLimit(máx. 1000) como rede de segurança GET /map/vehicles/:vehicleIdaceitatrailMode(points|sinceIgnition, defaultpoints) quandostartDate/endDatesão omitidos- em
points, a trilha usa a janela padrão de pontos - em
sinceIgnition, a trilha começa no último evento de ignição ligada encontrado na janela suportada; a resposta incluitrailModeefetivo eignitionOnAt(ISO ounullquando houver fallback) - sem
deviceIds, a trilha considera a cadeia de instalações do veículo na janela consultada, inclusive dispositivos já substituídos; cada ponto é recortado à vigência[createdAt, endedAt)da instalação naquele veículo (pacotes após uma troca de veículo não permanecem no veículo antigo); a posição ao vivo continua baseada apenas em instalações ativas - a trilha também mescla violações de cerca virtual (
packetTypeCode: 200/201) na janela consultada, com a mesma regra replace+inherit - pontos da trilha podem incluir
packetType/packetTypeCodequando disponíveis - o WebSocket
subscribe-vehicleaceita o mesmotrailModee os mesmosstartDate/endDate(a trilha histórica continua vindo do HTTP; o WS só anexa atualizações ao vivo) GET /speeding-reportanalisa a velocidade da trajetória contra os limites de via (PostGIS/OSM); aceitadeviceIds(vírgula),vehicleId,startDate/endDate,all,page/limit,organizationID(TRACKING exclusivo); exigespeeding-report:report- com
vehicleId, usa a cadeia histórica de instalações e recorta cada excesso à vigência[createdAt, endedAt)(não só a instalação ativa) - cada violação traz campos resumidos para tabela/mapa (
spdgps, coords,direction,roadMaxspeedKmh,excessKmh,highway,packetType/packetTypeCode) — não inclui mais o pacote bruto nem os campos internosmatchSource/deviceType(não consumidos pelo dashboard); useGET /device/packet-detailspara o pacote completo de um ponto específico - cada violação inclui
driver(motorista vinculado ao veículo na data/hora da violação, conforme o período do vínculo) GET /map/positionseGET /map/vehicles/:vehicleIdincluemdriver(motorista atualmente vinculado ao veículo — vínculo ativo comendDate = null), exceto quando TRACKING consulta um cliente viaorganizationID(motorista omitido)GET /event(relatório de eventos) incluidriverpor evento (motorista vinculado ao veículo na data/hora do evento), omitido no mesmo filtro de cliente TRACKING- o recorte operacional é a frota da organização (não quem recebeu o push): no instante do evento, o dispositivo estava instalado em um veículo daquele org (
[createdAt, endedAt)); sem instalação vigente, cai no vínculo atualDeviceCompanyRegister - eventos
geofence_violation/geofence_speed_limitexpõempositiona partir delat/lngdo payload,parameterssintéticos (direção+nome ou velocidade+limite) egeofenceIdquando presente no payload - filtros opcionais:
type(array/CSV denotificationType, ex.:3,4,geofence_violation,geofence_speed_limit),vehicleId(instalação vigente no instante do evento, não só a ativa),driverId(User id do motorista),organizationID(TRACKING: um cliente directory; default = home) - período (
startDate/endDate) e ordenação poreventTimestampusam a hora do pacote/evento (data.timestamp) com fallback paracreatedAt - ordenação opcional via
sortBy(eventTimestamp|createdAt|deviceID|notificationType) esortDir(asc|desc); defaulteventTimestamp desc
Exportações e notificações
- exportações grandes:
POST /report-export(job assíncrono) - tipos:
tracking,events,commands,user_activity - permissão por tipo:
tracking→tracking-report:report;events→event:read;commands→command:read;user_activity→user-activity:read - list/get/download exigem a permissão do tipo do job (listagem aceita qualquer uma delas)
- formatos:
xlsx,csv - para
tracking,filters.cleanStops(defaulttrue) reduz oscilação em pontos parado antes de gerar o arquivo - status em
GET /report-export/:id; download emGET /report-export/:id/file - ao concluir, a API emite notificação de sistema (
category=system,notificationType=report_export_ready) - o create aceita
notification(readyTitle/readyBody/failedTitle/failedBody) com placeholders{fileName},{rowCount},{error} GET /notificationaceita filtrocategory=event|systemGET /notification/unread-countsretorna contagens de não lidasGET /notification/historyretorna o histórico de notificações do usuário autenticadoPATCH /notification/read-allmarca todas as notificações como lidasPATCH /notification/:id/readmarca uma notificação específica como lidaPOST /notification/notifyenvia uma notificação de teste para o usuário autenticadoPOST /fcm-token/registerregistra o token de push do dispositivo;DELETE /fcm-tokeneDELETE /fcm-token/allremovem tokens do usuário autenticado
Chips (SimCard)
O módulo sim-card gerencia o inventário de chips SIM da empresa e o vínculo opcional com dispositivos.
Pontos relevantes:
GET /sim-cardlista o inventário da empresa TRACKING;organizationIDde um cliente directory devolve só chips instalados nos devices daquele cliente; omitido = estoque + chips que não estão em devices de clientes directory- campos obrigatórios:
iccid(único),phone,operatorID,brokerIDecompanyID(resolvido pelo contexto autenticado;masterdeve informarcompanyID) deviceIDopcional:null= estoque; preenchido = vinculado ao dispositivo- um dispositivo pode ter vários chips ativos ao mesmo tempo
POST /sim-card/:id/attachvincula sem desativar outros chips do devicePOST /sim-card/:id/detachdevolve o chip ao estoqueGET /sim-card/stocklista chips ativos sem dispositivoGET /sim-card/available-for-device/:deviceIDlista estoque elegível para o devicePOST /sim-card/assign-to-devicedefine o conjunto completo de chips do device ({ deviceID, simCardIDs[] }): IDs omitidos são desvinculados; lista vazia remove todos- exclusão é lógica (
statusID = inactive) e desvincula o dispositivo - catálogos auxiliares:
sim-card-operatoresim-card-broker - o payload de device inclui
simCards[]com os chips ativos vinculados - usuários de empresa operam apenas chips da própria empresa; attach/assign exige device na mesma empresa do chip
Implicações práticas:
- trate chip como recurso de inventário independente do cadastro de device
- para vínculo device↔SIM, prefira
available-for-device+assign-to-device - sincronize operadora e broker pelos endpoints de catálogo antes de criar o chip
Veículos
O módulo vehicle cobre o cadastro de veículos e os catálogos de marca, modelo e tipo.
Pontos relevantes:
- veículos são tenant-scoped pela empresa do contexto autenticado
- TRACKING lista a frota da home por padrão;
organizationIDde um cliente directory substitui o escopo emGET /vehicleeGET /vehicle/all(nunca mistura) - criação aplica
statusID = activepor padrão quando o campo é omitido - endpoints separados para
vehicle,vehicle-brand,vehicle-modelevehicle-type - a última posição do veículo depende dos dispositivos instalados e da telemetria consolidada pela API
- dispositivos disponíveis para instalação respeitam o escopo das empresas ativas vinculadas ao veículo
Implicações práticas:
- trate o veículo como recurso principal com escopo organizacional no token
- sincronize marcas, modelos e tipos como catálogos auxiliares
GET /vehicle/allretorna todos os veículos da empresa sem paginaçãoGET /vehicle/:vehicleID/available-deviceslista os dispositivos elegíveis para instalação no veículo (mesmo escopo de empresa)GET /vehicle/driver/:driverIDlista os veículos vinculados a um motorista- consuma monitoramento pelos endpoints públicos da API
Grupos de veículos (vehicle-group)
O módulo vehicle-group permite organizar a frota em grupos customizáveis por empresa (ex.: Frota A, Frota B), usados como alvo de cercas virtuais e futuras regras operacionais.
Pontos relevantes:
- recurso tenant-scoped;
masterinformacompanyIDna criação - membros são veículos com registro ativo na mesma empresa
PUT /vehicle-group/:id/memberssubstitui o conjunto completo de membros- exclusão é lógica (
statusID = inactive) - permissão de módulo:
vehicle-group(create|read|update|delete)
Endpoints:
| Método | Rota | Descrição |
|---|---|---|
POST | /vehicle-group | Criar grupo (name, vehicleIDs?) |
GET | /vehicle-group | Listar grupos do escopo |
GET | /vehicle-group/:id | Detalhe do grupo |
PATCH | /vehicle-group/:id | Atualizar nome/descrição/membros |
PUT | /vehicle-group/:id/members | Substituir membros |
DELETE | /vehicle-group/:id | Soft-delete |
Cercas virtuais (geofence)
O módulo geofence gerencia cercas virtuais desenhadas no mapa (polígono ou círculo), com gatilhos de entrada/saída e escopo de aplicação.
Pontos relevantes:
- recurso tenant-scoped;
masterinformacompanyIDna criação geometryaceita:- polígono:
{ "type": "polygon", "points": [{ "lat", "lng" }, ...] }(≥ 3 pontos) - círculo:
{ "type": "circle", "center": { "lat", "lng" }, "radiusMeters": number } triggerEnter/triggerExit: pelo menos um deve sertrue, ouspeedLimitKmh> 0 (cerca só de velocidade)speedLimitKmhopcional (km/h): enquanto o veículo está dentro espdgpssupera o limite, a API emite evento servidor 201 (geofence_speed_limit) em rising-edge- escopo obrigatório:
applyToCompany: trueou ≥1vehicleIDsou ≥1vehicleGroupIDs - veículos e grupos devem pertencer à mesma empresa da cerca
coloropcional (hex#RRGGBB) para renderização no cliente- exclusão é lógica (
statusID = inactive) - permissão de módulo:
geofence(create|read|update|delete)
Presets de município (IBGE): catálogo nacional em PostGIS (roads-postgres.city_boundaries), populado via tools/roads/import-cities.sh. Não é tenancy — qualquer usuário com geofence:read pode buscar e aplicar um polígono no editor; a cerca salva continua sendo a Geofence tenant (cópia JSONB).
| Método | Rota | Descrição |
|---|---|---|
GET | /geofence/presets/cities?q=&uf=&limit= | Busca municípios por nome (prefixo, min. 2 chars) |
GET | /geofence/presets/cities/at?lat=&lng= | Município que contém o ponto WGS84 |
GET | /geofence/presets/cities/:ibgeCode | Geometria pronta { type: 'polygon', points } (maior anel; partsOmitted se houver ilhas) |
Se o sidecar PostGIS não estiver configurado, esses endpoints respondem 503. O CRUD manual de cercas não depende deles.
Busca de endereços (Photon): proxy autenticado para o geocoder OSM Brasil (PHOTON_URL). Serve para centralizar o mapa no editor de cercas (não aplica geometria). Resposta normalizada (não GeoJSON cru):
[
{
"id": "W:171721829",
"label": "Avenida Paulista — Paulista — Pernambuco — 53417-400",
"name": "Avenida Paulista",
"type": "street",
"city": "Paulista",
"state": "Pernambuco",
"postcode": "53417-400",
"lat": -7.9314398,
"lng": -34.8882381,
"extent": [-34.8899743, -7.9314988, -34.8863776, -7.9307134]
}
]
| Método | Rota | Descrição |
|---|---|---|
GET | /geofence/presets/addresses?q=&limit= | Busca ruas/lugares (min. 2 chars; limit 1–15, default 10) |
extent é [minLng, minLat, maxLng, maxLat] quando o Photon envia bounding box; caso contrário null. Sem PHOTON_URL ou sidecar indisponível → 503.
Alerta de violação (server-side): após persistir telemetria, o sigme_packet_consumer publica GPS leve em geofence_queue. A API compara ponto×geometria (círculo/polígono), mantém GeofencePresence e:
- transição enter/exit (respeitando
triggerEnter/triggerExit) →GeofenceViolationLogkindboundary+ notificaçãogeofence_violation(código sintético 200) - rising-edge de excesso de velocidade dentro da cerca (
speedLimitKmh) → kindspeed_limit+ notificaçãogeofence_speed_limit(código 201)
Faixa de códigos: 1–199 eventos do rastreador; 200–255 eventos gerados pelo servidor.
{
"type": "geofence_violation",
"payload": {
"deviceId": "abc123",
"title": "Geofence exit",
"body": "Vehicle ABC1D23 exited Yard",
"notificationType": "geofence_violation",
"category": "event",
"data": {
"geofenceId": "1",
"direction": "exit",
"violationLogId": "99"
}
}
}
- Não reutiliza packtype firmware
15/FENCE/geofence_alertnem6/VEL. MAX. - Preferências:
"geofence_violation"e"geofence_speed_limit"(defaults enabled). - Destinatários: tokens FCM da empresa do dispositivo com a preferência ativa (
sigme_notifications). - Primeira observação de um par (cerca, veículo) só inicializa presença — sem push/log.
- Permanecer fora/dentro não reenvia boundary; permanecer acima do limite não reenvia speed (só rising-edge).
- No relatório de eventos (
GET /event),positionvem dedata.lat/data.lng,parameterssintetiza direção/nome (boundary) ou speed/limit (201), egeofenceIdé exposto para o cliente carregar a geometria viaGET /geofence/:id.
Relatório de rastreamento / mapa / rota: violações entram como highlighted (mapRole: badge, códigos 200/201). No mesmo deviceId + segundo, o pacote routine é substituído pela violação, que herda velocidade e demais telemetria do pacote. A mesma regra vale em GET /device/tracking-report, trilha de GET /map/vehicles/:vehicleId (e WS) e GET /device/route/:deviceId.
Endpoints:
| Método | Rota | Descrição |
|---|---|---|
POST | /geofence | Criar cerca virtual |
GET | /geofence | Listar cercas do escopo |
GET | /geofence/presets/addresses | Buscar endereços (Photon) |
GET | /geofence/presets/cities | Buscar presets IBGE por nome |
GET | /geofence/presets/cities/at | Município no ponto (lat/lng) |
GET | /geofence/presets/cities/:ibgeCode | Geometria do preset |
GET | /geofence/:id | Detalhe da cerca |
PATCH | /geofence/:id | Atualizar cerca |
DELETE | /geofence/:id | Soft-delete |
Instalações
O módulo installation gerencia o vínculo entre dispositivos e veículos.
Pontos relevantes:
- a criação de instalação valida a posse do dispositivo (vínculo empresa/dispositivo ativo) e o escopo do veículo
- usuários de empresa só leem/mutam instalações de veículos da própria empresa;
masteropera sem essa restrição - a cadeia de instalações do veículo determina quais dispositivos compõem a trilha histórica (inclusive dispositivos já substituídos) nas janelas cobertas
- catálogo auxiliar:
installation-type
Endpoints:
| Método | Rota | Descrição |
|---|---|---|
POST | /installation | Criar instalação (vincular device a veículo) |
PATCH | /installation/remove-from-vehicle | Remover dispositivo de um veículo |
GET | /installation | Listar instalações (tenant) |
GET | /installation/:id | Detalhe de uma instalação |
PATCH | /installation/:id | Atualizar instalação |
DELETE | /installation/:id | Excluir instalação |
Permissões e Defaults
Perfis default de permissão usam o formato module -> action[].
Consequências práticas:
- respostas autenticadas carregam permissões prontas para consumo por módulo e ação
- não infira permissões a partir de labels de UI; o contrato é o payload da API
coloré um módulo de permissão próprio; funcionalidades do catálogo de cores exigem grants explícitos emcolorvehicle-groupegeofencesão módulos próprios; ADMIN recebe CRUD e USER recebereadnos defaults- mutações de catálogos de plataforma (
color, marcas/modelos/tipos de veículo, fabricantes/tipos/modelos de dispositivo, operadoras/brokers de SIM, cargos/tipos de usuário edefault-command) exigem contextomaster, além das permissões de módulo - papéis canônicos de sistema não podem ser renomeados ou removidos; papéis custom por empresa são gerenciáveis via API
- tipos canônicos de
user-typenão podem ser atualizados nem removidos via API
Comandos Padrão (default-command)
Catálogo de templates para seleção ao enviar comando a um dispositivo.
Contrato:
GET /default-commandeGET /default-command/:id— leitura para quem possuidefault-command:read,command:readoucommand:send- query opcional
activeOnly=trueretorna apenas templates ativos POST /default-command,PATCH /default-command/:id,DELETE /default-command/:id— mutações restritas amaster; delete inativa o registro- payload de criação/atualização:
name,command,description?,statusID? - o envio operacional continua em
POST /commandcom o campocommandjá resolvido
Comandos
Envio e acompanhamento de comandos a dispositivos.
POST /command— envia um comando ao dispositivo (command:send)POST /command/cancel— cancela comandos pendentes ({ "ids": string[] })GET /command— lista os comandos enviados no escopo da empresa (command:read)- aceita
organizationIDexclusivo (TRACKING; default = home) - cada comando inclui
driver(motorista vinculado ao veículo na data/hora do comando, conforme o período do vínculo), omitido no filtro de cliente - ordenação opcional via
sortBy(createdAt|command|deviceId) esortDir(asc|desc); defaultcreatedAt desc - o template de seleção fica em
/default-command(seção acima)
Preferências de Notificação
O módulo preferences concentra as preferências de notificação por vínculo usuário/empresa (anteriormente chamadas de "parameters").
Pontos relevantes:
GET /preferences/default— catálogo default de eventos de alerta (settings:read)GET /preferences— preferências do usuário autenticado (preferences:read); cai no default quando não há personalizaçãoPATCH /preferences— atualiza as preferências do usuário autenticado (preferences:update)- o contrato usa
eventscomo coleção principal (frota da própria empresa) - cada evento pode expor identificador, nome técnico, label, estado (
value), categoria e visibilidade (show) - operadores TRACKING podem enviar
clientAlerts: mapa{ "all": { "events": [...] }, "<companyIdDoCliente>": { "events": [...] } } - a chave
allé o baseline compartilhado (clientes atuais e futuros); chaves numéricas só somam eventos extras — não removem o que está emall - cliente sem chave numérica ainda herda
all; semalle sem chave do cliente, não há push TRACKING (opt-in) - usuários CLIENT ignoram
clientAlertse usam sóeventsda própria frota - sincronize o catálogo pela API para evitar drift entre defaults e personalizações
Parâmetros da Empresa
O módulo parameters guarda parâmetros do sistema por empresa (documento JSONB vinculado à empresa).
Pontos relevantes:
GET /parameters— retorna os parâmetros da empresa do usuário autenticado (parameters:read); usuáriosmasterpodem passar?companyId=para ler outra empresaPATCH /parameters— atualiza os parâmetros da empresa, mesclando as chaves de topo enviadas (parameters:update);masterpode passar?companyId=- a chave
examsconfigura os exames periódicos dos motoristas: cada item possuitype,enabledevalidityDays(validade em dias; ver seção "Validade dos exames") - o acesso é escopado à empresa do usuário autenticado; apenas
masterconsegue visar outra empresa
Integração em Tempo Real
A plataforma publica canais WebSocket para atualização operacional.
Pontos relevantes:
- autenticação do canal é obrigatória
- o gateway
/location-streamaceita no handshake Socket.io: - JWT:
auth: { token: '<jwt>' }ou headerAuthorization: Bearer <jwt> - API Key:
auth: { apiKey: '<chave>' } - payloads de localização e trilha são entregues já consolidados pela API
Recomendações:
- use realtime quando precisar de baixa latência ou atualização contínua
- use REST/OpenAPI como base de onboarding e integração inicial
- com API Key, conecte o WebSocket com
auth: { apiKey }no handshake
Tratamento de Erros
Clientes devem estar preparados para:
400 Bad Request— payload inválido ou regra de domínio violada401 Unauthorized— autenticação inválida, ausente ou expirada403 Forbidden— operação fora da permissão ou escopo404 Not Found— recurso inexistente409 Conflict— violação de unicidade5xx— falha interna ou indisponibilidade temporária
Recomendações:
- retry apenas para falhas transitórias apropriadas
- não usar retry cego para
4xx - correlacionar request, tenant e resposta recebida
Requisitos para Integração Corporativa
Considere desde o início:
- gestão segura de JWT e chaves de API
- separação entre homologação e produção
- observabilidade de chamadas, erros e latência
- rotação de credenciais
- gestão de escopo por empresa e por papel
- versionamento do cliente para payloads consumidos
- testes automatizados de contrato nos endpoints críticos
Boas Práticas de Consumo
- use o OpenAPI como referência primária de endpoint, parâmetros e schema
- trate catálogos operacionais como contratos conhecidos e sincronizáveis pela API
- não acoplar integrações a comportamentos não documentados
- respeite o modelo multiempresa em todas as integrações
- isole credenciais por cliente, empresa ou ambiente
- revise periodicamente permissões e superfícies expostas
Recomendação de Onboarding para Empresas Integradoras
- validar acesso ao ambiente e à documentação OpenAPI
- alinhar autenticação e credenciais técnicas
- mapear o tenant e o escopo funcional da integração
- integrar catálogos e cadastros-base
- integrar fluxos operacionais e, por fim, realtime quando necessário
- formalizar monitoramento, rotação de credenciais e testes de regressão
Observação Final
Este guia deve evoluir com a API. Sempre que uma superfície pública relevante mudar, atualize a documentação com o contrato atual de consumo.