Pular para o conteúdo principal

Workflows — Motor de Orquestração de Notificações

O sistema de Workflows do Notifica permite definir sequências de passos para orquestrar o envio de notificações de forma automatizada. Com workflows, você pode criar fluxos como: enviar um email, aguardar 1 hora, verificar se foi entregue, e se não, enviar por WhatsApp como fallback.

Conceitos

O que é um Workflow?

Um workflow é uma sequência de até 10 passos que executa em ordem para um destinatário. Cada workflow pertence a um tenant e é identificado por um slug único (URL-safe).

Tipos de Passos

TipoDescriçãoCampos obrigatórios
sendEnvia uma notificação por um canal + templatechannel, template
delayPausa a execução por uma duraçãoduration (ex: 5m, 1h, 1d)
fallbackTenta canais em ordem até sucessochannels (lista), template

Formatos de Duração (Delay)

FormatoSignificadoExemplo
NmN minutos30m = 30 minutos
NhN horas2h = 2 horas
NdN dias1d = 1 dia
aviso

O delay máximo é de 7 dias (168h). Durações maiores serão rejeitadas na validação.


Modelo de Execução

Como o Engine funciona

O Notifica usa Oban (sistema de filas baseado em PostgreSQL) para orquestrar a execução dos workflows:

  1. Trigger → Cria um WorkflowRun com status running e enfileira um job para o passo 0
  2. Passo send → Cria uma notificação via Messaging.create_notification e avança imediatamente para o próximo passo (no mesmo job)
  3. Passo delay → Agenda um novo job Oban para o horário futuro e para a execução atual
  4. Passo fallback → Verifica se o envio anterior foi entregue. Se não, tenta os canais na lista em ordem até um sucesso

Ciclo de Vida de um Run

running → completed    (todos os passos executados com sucesso)
→ failed (um passo falhou sem recovery)
→ cancelled (cancelado via API)

Idempotência

Cada execução de passo gera uma chave de idempotência no formato:

wfrun:<run_id>:step:<index>

Para fallback com múltiplos canais:

wfrun:<run_id>:step:<index>:ch:<channel>

Isso garante que retentativas do Oban não criem notificações duplicadas.

Versionamento

Workflows usam versionamento imutável. Ao atualizar um workflow:

  1. A versão atual é desativada (active: false)
  2. Uma nova versão é criada com version incrementado
  3. Runs em andamento continuam com a versão capturada no momento do trigger
informação

Isso significa que atualizar um workflow nunca afeta execuções já em andamento.


API — CRUD de Workflows

Criar um Workflow

curl -X POST https://app.usenotifica.com.br/v1/workflows \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: wf-welcome-v1" \
-d '{
"slug": "welcome-onboarding",
"name": "Onboarding de Boas-Vindas",
"steps": [
{
"type": "send",
"channel": "email",
"template": "welcome-email"
},
{
"type": "delay",
"duration": "1h"
},
{
"type": "fallback",
"channels": ["whatsapp", "sms"],
"template": "welcome-reminder",
"condition": "not_delivered"
}
]
}'

Resposta (201 Created):

{
"data": {
"id": "550e8400-e29b-41d4-a716-446655440000",
"slug": "welcome-onboarding",
"name": "Onboarding de Boas-Vindas",
"steps": [
{"type": "send", "channel": "email", "template": "welcome-email"},
{"type": "delay", "duration": "1h"},
{"type": "fallback", "channels": ["whatsapp", "sms"], "template": "welcome-reminder", "condition": "not_delivered"}
],
"version": 1,
"active": true,
"inserted_at": "2025-02-03T15:30:00Z",
"updated_at": "2025-02-03T15:30:00Z"
}
}

Listar Workflows

curl https://app.usenotifica.com.br/v1/workflows \
-H "Authorization: Bearer YOUR_API_KEY"

Resposta (200 OK):

{
"data": [
{
"id": "550e8400-...",
"slug": "welcome-onboarding",
"name": "Onboarding de Boas-Vindas",
"steps": [...],
"version": 2,
"active": true,
"inserted_at": "2025-02-03T15:30:00Z"
}
]
}

Obter um Workflow

curl https://app.usenotifica.com.br/v1/workflows/550e8400-e29b-41d4-a716-446655440000 \
-H "Authorization: Bearer YOUR_API_KEY"

Atualizar um Workflow

A atualização cria uma nova versão. O slug pode ser mantido ou alterado.

curl -X PUT https://app.usenotifica.com.br/v1/workflows/550e8400-e29b-41d4-a716-446655440000 \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Onboarding v2",
"steps": [
{"type": "send", "channel": "email", "template": "welcome-email-v2"},
{"type": "delay", "duration": "30m"},
{"type": "send", "channel": "push", "template": "welcome-push"}
]
}'

Resposta (200 OK):

{
"data": {
"id": "nuevo-uuid-da-nova-versao",
"slug": "welcome-onboarding",
"name": "Onboarding v2",
"version": 2,
"steps": [...],
"active": true
}
}

Deletar um Workflow (Soft Delete)

curl -X DELETE https://app.usenotifica.com.br/v1/workflows/550e8400-e29b-41d4-a716-446655440000 \
-H "Authorization: Bearer YOUR_API_KEY"

Resposta: 204 No Content

informação

A deleção é soft — o workflow é marcado como active: false. Runs em andamento continuam executando.


API — Trigger de Workflows

Disparar um Workflow

Use o slug do workflow para dispará-lo para um destinatário:

curl -X POST https://app.usenotifica.com.br/v1/workflows/welcome-onboarding/trigger \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: trigger-user-123-welcome" \
-d '{
"recipient": "[email protected]",
"data": {
"name": "João",
"company": "Empresa Ltda",
"plan": "pro"
}
}'

Resposta (202 Accepted):

{
"data": {
"id": "run-uuid-here",
"workflow_id": "550e8400-...",
"workflow_version": 2,
"recipient": "[email protected]",
"status": "running",
"current_step": 0,
"step_results": [],
"data": {"name": "João", "company": "Empresa Ltda", "plan": "pro"},
"started_at": "2025-02-03T16:00:00Z"
}
}
dica

O campo data é passado como payload para os templates nos passos send e fallback. Use variáveis como {{name}} nos seus templates.

Campos aceitos no trigger:

CampoObrigatórioDescrição
recipient ou toSimEndereço do destinatário (email, telefone, etc.)
data ou payloadNãoDados de template/payload (map)

API — Workflow Runs (Execuções)

Listar Execuções

curl "https://app.usenotifica.com.br/v1/workflow-runs?limit=20" \
-H "Authorization: Bearer YOUR_API_KEY"

Parâmetros de query:

ParâmetroTipoDescrição
limitintMáximo de resultados (default: 50)
statusstringFiltrar por status: running, completed, failed, cancelled
workflow_iduuidFiltrar por workflow específico

Resposta (200 OK):

{
"data": [
{
"id": "run-uuid",
"workflow_id": "wf-uuid",
"workflow_version": 2,
"recipient": "[email protected]",
"status": "completed",
"current_step": 3,
"step_results": [
{"type": "send", "step": 0, "channel": "email", "notification_id": "notif-uuid", "status": "enqueued"},
{"type": "delay", "step": 1, "duration": "1h", "duration_seconds": 3600, "scheduled_at": "..."},
{"type": "fallback", "step": 2, "status": "skipped", "reason": "previous step already delivered"}
],
"started_at": "2025-02-03T16:00:00Z",
"completed_at": "2025-02-03T17:00:05Z"
}
]
}

Obter Detalhes de uma Execução

curl https://app.usenotifica.com.br/v1/workflow-runs/run-uuid-here \
-H "Authorization: Bearer YOUR_API_KEY"

A resposta inclui step_results com o resultado detalhado de cada passo executado.

Cancelar uma Execução

curl -X POST https://app.usenotifica.com.br/v1/workflow-runs/run-uuid-here/cancel \
-H "Authorization: Bearer YOUR_API_KEY"

Resposta (200 OK):

{
"data": {
"id": "run-uuid",
"status": "cancelled",
"completed_at": "2025-02-03T16:30:00Z",
"step_results": [...]
}
}
aviso

Cancelar um run apenas impede que passos futuros executem. Notificações já enviadas nos passos anteriores não são revertidas.

Resposta (409 Conflict): Se o run já está em status terminal (completed, failed, ou cancelled).


Exemplos Práticos

Onboarding com Fallback Multi-Canal

{
"slug": "user-onboarding",
"name": "Onboarding Completo",
"steps": [
{"type": "send", "channel": "email", "template": "welcome-email"},
{"type": "delay", "duration": "2h"},
{"type": "fallback", "channels": ["push", "whatsapp"], "template": "welcome-reminder", "condition": "not_delivered"},
{"type": "delay", "duration": "1d"},
{"type": "send", "channel": "email", "template": "setup-guide"}
]
}

Lembrete de Pagamento Escalonado

{
"slug": "payment-reminder",
"name": "Lembrete de Pagamento",
"steps": [
{"type": "send", "channel": "email", "template": "payment-due-email"},
{"type": "delay", "duration": "3d"},
{"type": "send", "channel": "sms", "template": "payment-due-sms"},
{"type": "delay", "duration": "4d"},
{"type": "fallback", "channels": ["whatsapp", "push"], "template": "payment-overdue", "condition": "not_delivered"}
]
}

Confirmação de Pedido Simples

{
"slug": "order-confirmation",
"name": "Confirmação de Pedido",
"steps": [
{"type": "send", "channel": "email", "template": "order-confirmation"},
{"type": "send", "channel": "push", "template": "order-push"}
]
}

Validações e Limites

RegraLimite
Máximo de passos por workflow10
Delay máximo7 dias
SlugLowercase alfanumérico + hífens/underscores, 1-100 chars
Nome1-255 caracteres
Steps sendObrigatório: channel + template
Steps delayObrigatório: duration (formato: Nm, Nh, Nd)
Steps fallbackObrigatório: channels (lista) + template

Referências