Appearance
Audit Log — registro de ações na plataforma
Toda ação relevante executada no flow-ai-core é registrada na tabela audit_logs do PostgreSQL. O sistema cobre eventos de autenticação, CRUD de entidades administrativas e tarefas de sistema (retenção de logs).
Visão geral
| Aspecto | Decisão |
|---|---|
| Storage | Tabela audit_logs no mesmo PostgreSQL |
| Escrita | Fire-and-forget (não bloqueia a operação principal) |
| Retenção | AUDIT_LOG_RETENTION_DAYS dias (padrão: 90) |
| Acesso | Permissão RBAC audit_logs:read |
| Scoping | Grupos com routerIds só veem logs do(s) seu(s) router(s) |
Schema
prisma
model AuditLog {
id String @id @default(cuid())
action AuditAction
entityType AuditEntityType?
entityId String?
actorId String?
actor User? @relation(...)
routerId String? // sem FK — preservado após deleção do Router
status AuditStatus @default(success)
changes Json?
metadata Json?
createdAt DateTime @default(now())
}changes
| Ação | Formato |
|---|---|
CREATE | Snapshot do objeto criado (sem campos sensíveis) |
UPDATE | { campo: { from, to } } — só campos alterados |
DELETE | Snapshot do objeto deletado (sem campos sensíveis) |
| Auth / sistema | null |
Campos sensíveis nunca entram em changes (lista SENSITIVE_FIELDS em utils/audit.ts): password, passwordHash, tokenHash, accessTokenEncrypted, metaAppSecretEncrypted, encryptionPrivateKeyEncrypted, encryptionPassphraseEncrypted, apiKeyEncrypted, valueEncrypted. Além disso, buildChanges() ignora createdAt e updatedAt.
metadata
Para eventos HTTP contém { ip, userAgent }. Alguns eventos de auth também incluem email no metadata (falha de LOGIN e PASSWORD_CHANGE, onde ainda não há actorId). Null para eventos de sistema sem contexto HTTP (ex: RETENTION_CLEANUP).
Enum AuditAction
| Valor | Quando é emitido |
|---|---|
LOGIN | Login bem-sucedido ou com falha via /auth/login e /auth/desk-login |
TOKEN_REFRESH | Renovação de tokens via /auth/refresh |
LOGOUT | Logout via /auth/logout |
PASSWORD_CHANGE | Troca de senha via /auth/password-recovery/validate |
CREATE | Criação de entidade auditada |
UPDATE | Atualização de entidade auditada |
DELETE | Deleção de entidade auditada |
PUBLISH | Publicação de flow (POST /flows/:id/publish) |
UNPUBLISH | Reservado no enum — ainda não é emitido por nenhuma rota |
CAMPAIGN_DISPATCHED | Reservado no enum — ainda não é emitido por nenhuma rota |
RETENTION_CLEANUP | Limpeza automática de logs expirados |
Nota:
UNPUBLISHeCAMPAIGN_DISPATCHEDexistem apenas no enum e no filtro do endpoint de consulta; nenhuma rota grava esses eventos hoje.PUBLISHé emitido de fato, mas somente paraFLOW(não há publicação de tool auditada).
Enum AuditEntityType
Lista completa (verbatim do schema.prisma):
prisma
enum AuditEntityType {
USER
ROUTER
WHATSAPP_NUMBER
FLOW
PUBLISHED_FLOW
TOOL
PUBLISHED_TOOL
AGENT
AGENT_GROUP
AI_AGENT
DEPARTMENT
QUEUE
LLM_CREDENTIAL
INTEGRATION_SERVER
INTEGRATION_SERVER_ENDPOINT
MESSAGE_TEMPLATE
CAMPAIGN
SCRIPT_TEMPLATE
SYSTEM_PROMPT
GUARDRAIL
FLOW_VARIABLE
ROUTER_VARIABLE
API_CLIENT
WEBCHAT_CHANNEL
}Entidades efetivamente instrumentadas
Apesar de o enum listar 24 tipos, hoje apenas quatro rotas gravam audit logs de CRUD:
entityType | Ações emitidas | Rota |
|---|---|---|
USER | CREATE, UPDATE, DELETE | user.routes.ts (PUT e PATCH ambos emitem UPDATE) |
ROUTER | CREATE, UPDATE, DELETE | router.routes.ts |
FLOW | CREATE, UPDATE, DELETE, PUBLISH | flow.routes.ts |
API_CLIENT | CREATE, UPDATE, DELETE | api-client.routes.ts |
Os demais entityType existem no enum (e são aceitos como filtro no endpoint de consulta), mas ainda não têm nenhuma rota que grave esses eventos.
Endpoint de consulta
GET /api/audit-logsPermissão: audit_logs:read
Query params:
| Param | Tipo | Descrição |
|---|---|---|
action | enum AuditAction | Filtra por tipo de ação |
entityType | enum AuditEntityType | Filtra por tipo de entidade |
actorId | string | Filtra por usuário que executou |
routerId | string | Filtra por router |
status | success | failure | Filtra por resultado |
from | ISO 8601 datetime | Data início |
to | ISO 8601 datetime | Data fim |
cursor | string (cuid) | Cursor para paginação |
limit | int 1–200 | Registros por página (padrão 50) |
Resposta:
json
{
"items": [
{
"id": "...",
"action": "UPDATE",
"entityType": "USER",
"entityId": "...",
"actorId": "...",
"actor": { "id": "...", "name": "João", "email": "joao@..." },
"routerId": null,
"status": "success",
"changes": { "name": { "from": "João", "to": "João Silva" } },
"metadata": { "ip": "10.0.1.2", "userAgent": "Mozilla/..." },
"createdAt": "2026-05-19T12:34:56.000Z"
}
],
"nextCursor": "clxxx..."
}Scoping por router
Grupos RBAC com routerIds não vazios só enxergam audit logs cujo routerId está dentro do array. Admins (userRole=admin) e grupos globais veem tudo.
Retenção
O worker startAuditRetentionWorker roda em background no flow-ai-core via runPollingLoop. A cada hora executa dois ciclos de limpeza:
audit_logs— deleta todos os registros comcreatedAt < now() - AUDIT_LOG_RETENTION_DAYS dias(padrão 90). Só quando remove pelo menos um registro (count > 0), grava um eventoRETENTION_CLEANUPcomchanges = { deletedCount, cutoffDate }(semactorIdnemmetadata).agent_turns— o mesmo worker também purga registros do AI Debugger com retenção fixa de 30 dias (AGENT_TURNS_RETENTION_DAYS). Essa limpeza não gera evento de audit log.
env
# Padrão: 90 dias (agent_turns usa 30 dias fixos)
AUDIT_LOG_RETENTION_DAYS=90Arquivos relevantes
| Arquivo | Papel |
|---|---|
packages/flow-ai-database/prisma/schema.prisma | Modelo AuditLog, enums AuditAction/EntityType/Status |
packages/flow-ai-database/prisma/migrations/20260519000000_add_audit_logs/ | Migration que cria a tabela |
services/flow-ai-core/src/services/audit-log.service.ts | AuditLogService — write(), writeFromActor(), list() |
services/flow-ai-core/src/utils/audit.ts | extractActorContext(), buildChanges(), sanitizeEntity() |
services/flow-ai-core/src/consumers/audit-retention.worker.ts | Worker de retenção (poll a cada 1h) |
services/flow-ai-core/src/http/routes/audit-log.routes.ts | GET /audit-logs |
services/flow-ai-core/src/services/factories/makeAuditLogService.ts | Factory de DI do AuditLogService |
services/flow-ai-core/src/http/routes/auth.routes.ts | Audit de LOGIN/LOGOUT/TOKEN_REFRESH/PASSWORD_CHANGE |
services/flow-ai-core/src/http/routes/user.routes.ts | Audit de USER CREATE/UPDATE/DELETE |
services/flow-ai-core/src/http/routes/router.routes.ts | Audit de ROUTER CREATE/UPDATE/DELETE |
services/flow-ai-core/src/http/routes/flow.routes.ts | Audit de FLOW CREATE/UPDATE/DELETE/PUBLISH |
services/flow-ai-core/src/http/routes/api-client.routes.ts | Audit de API_CLIENT CREATE/UPDATE/DELETE |