Domain (EventStorming)
Mapeamento estilo EventStorming (Alberto Brandolini) do domínio financeiro Blueprintt × Omie. Naranja = evento (passado, imutável), azul = comando (intenção), lilás = política (quando X então Y), amarelo = agregado / ator, rosa = sistema externo, verde = read model, vermelho = hotspot / dúvida. Fluxo esquerda→direita é o tempo. Eventos usam PascalCase canônico do catálogo — são IDs duráveis do domínio.
Legenda
Section titled “Legenda”Big Picture — fluxo principal
Section titled “Big Picture — fluxo principal”Do clique de compra à NF emitida — caminho feliz, PJ AABC com pagamento via Pagar.me.
Bounded Contexts
Section titled “Bounded Contexts”Quatro contextos em swimlanes paralelas. Cada um tem seu agregado raiz, eventos próprios e comandos exclusivos. A integração ocorre via eventos de domínio publicados pelo backend orquestrador.
Swimlane 1 — Order Lifecycle
Agregado raiz: Order. Status duplo independente (status_pedido × status_faturamento). Idempotência por bubble_order_id.
Swimlane 2 — Payment
Agregado raiz: Pagamento. Gateway externo Pagar.me. Webhook charge.* com HMAC obrigatório. TED/depósito bypass (sem charge_id, confirmação manual).
Swimlane 3 — Billing & NF
Agregados raiz: OrdemDeServico + NFSe. Engine de regras determinística (decide_billing()). Invoice Ledger append-only, máximo 1 linha emitted por Order.
Swimlane 4 — Carta de Crédito
Agregado raiz: CartaDeCredito. Gerada por cancelamento de Pedido com pagamento confirmado (via Modal Decisão Financeira) ou cancelamento de Participante (proporcional). Transferível PF↔PJ. Uso total ou parcial (complemento via Pagar.me).
Aggregates
Section titled “Aggregates”Boundaries de consistência. Cada agregado é o único ponto de entrada para mutação dos seus dados — operações externas passam por comandos.
Aggregate · Order
OrderStatus duplo: status_pedido (3 valores) × status_faturamento (9 valores) independentes. Consistência de transição via state machine. Origem ∈ backoffice.
Aggregate · Customer
CustomerPF ou PJ. CNPJ é chave de idempotência no Omie. Razão social, email e endereço espelhados. Brasil API auto-preenche cadastro PJ.
Aggregate · OrdemDeServico
OrdemDeServicoOS Omie criada por ordens_servico.incluir. Pré-requisito para faturamento e NF-e. Vinculada a Projeto Omie (por Evento) e Cliente Omie (por CNPJ). Não recriada se já existe.
Aggregate · NFSe
NFSeDocumento fiscal terminal. Uma vez emitida, exige operação explícita de cancelamento. Invoice Ledger garante no máximo 1 emissão por Order. Campos: omie_nfe_id, nfe_number, nfe_key.
Aggregate · Pagamento
PagamentoCobrança Pagar.me com charge_id + idempotency_key. TED/depósito modelado sem charge_id, confirmação manual operador. Webhook HMAC obrigatório.
Aggregate · CartaDeCredito
CartaDeCreditoRaiz separada. Geração só por cancelamento (Pedido com pagamento confirmado ou Participante). Nunca inserção manual. Transferível PF↔PJ. Uso total ou parcial.
Aggregate · Vendedor
VendedorUsuário Blueprintt com flag is_vendedor=true. Vinculado ao Pedido (não ao ingresso). Recebe alerta cada 7 dias quando Pedido fica “Aguardando confirmação” sem liberação.
Aggregate · Participante
ParticipantePessoa física no evento. Status: ativo | cancelado. Cancelar ajusta quantidade OS Omie. Se NFS-e emitida, gera CC proporcional (não cancela nota).
Aggregate · Evento
EventoSigla → nome Projeto Omie. Nome completo → descrição OS/NFS-e. Cidade do evento determina tipo de serviço Omie + cidade de prestação.
Aggregate · TipoServicoOmie
TipoServicoOmieMapa (cidade × flag órgão público) → código Omie. SP/RJ mapeados; outras cidades = seleção manual. Lista consultada dinâmica via /servicos/listaservico/.
Policies
Section titled “Policies”Reações automáticas — “when X then Y”. Codificadas no engine de billing, no webhook handler e no engine de cancelamento.
Billing scheduling
When PaymentConfirmed → then BillingScheduledPF: agendamento imediato. PJ com requires_manual_confirmation=true: cai em BillingHoldCreated. PJ padrão: passa pela Regra do Dia 25.
Cutoff dia 25
When today > dia 25 ∧ PJ ∧ data desejada no mesmo mês → then Day25BlockAppliedFaturamento adia para 1º dia útil do mês seguinte. PF nunca cai nessa regra. Override pelo operador exige motivo + log (Day25Overridden).
Boleto expirado
When BoletoExpired → then EmailSentNotificação automática ao comprador. Status do Pedido permanece aguardando_pagamento até nova tentativa ou cancelamento.
Cancelamento de Pedido
When OrderCancelled (pré-NF) → then OS Omie cancelada · CancelarNFSe NÃO aplicávelPós-NF: dispara modal financeiro com RefundDecided → IssueCartaDeCredito OU RefundPayment. NFS-e pode exigir InvoiceCancelled separado.
Webhook Pagar.me
When webhook charge.* + HMAC inválido → then reject 401, no eventValidação X-Hub-Signature com PAGARME_WEBHOOK_SECRET. HTTP 200 imediato apenas se assinatura válida. Processamento assíncrono pós-200. Idempotência por data.id.
Rate limit Omie
When Omie REDUNDANT → then wait hint + 5s · When HTTP 425 → then ban 31minREDUNDANT classificado como OmieValidationError (não-retryable). HTTP 425 nunca retentar antes de 31 min — reinicia contador. Discovery BLU-783; implementação pendente.
Hotspots
Section titled “Hotspots”Dúvidas e riscos em aberto. Cada hotspot bloqueia ou degrada uma capacidade do MVP até resolução.
P11 · Formato vendedor
⚠ Formatovendedor na O.S. — array de IDs ou string nome?Consultar /geral/vendedores/ antes de implementar. Bloqueia campo vendedor no payload OS.
P12 · Homologação NFS-e
⚠ Ambiente homologação NFS-e — acesso 7d, qual Prefeitura?Toggle Homologação cobre só envelope NFS-e. Algumas Prefeituras não têm homologação — verificar antes de smoke. Pegadinha em ambiente Demonstração.
BUBBLE-1 · Webhook Pagar.me legacy
⚠ Bubble já recebe webhook Pagar.me direto? Substituir ou convive?Bubble tem pagarmedetails + pagarmewebhookcall no schema. Confirmar se backend substitui o handler atual ou roda em paralelo.
OMIE-1 · Cache TTL serviços
⚠ Cache TTL/servicos/listaservico/ — quanto tempo?Lista de serviços consultada dinamicamente, não hard-coded. Refresh diário é hipótese — confirmar TTL e estratégia de invalidação.
PAGARME-1 · Secret webhook
⚠PAGARME_WEBHOOK_SECRET rotacionado/válido em produção?Sem secret válido, HMAC sempre falha e nenhum PaymentConfirmed é processado. Bloqueia smoke real.
Gap 4 · Enum status writeback
⚠ Enum status writeback PT vs EN inconsistentesync_service.py:430 escreve “NF emitida” (PT) vs invoice_service.py:222 escreve “invoiced” (EN). Confirmar Option Set ns_status canonical do Bubble com Luiz.
BLU-783 · Rate-limit Omie
⚠ Discovery existe, implementação pendentePolítica REDUNDANT + 425 documentada, falta ticket filho de implementação. Sem ela, retries agressivos podem causar ban 31 min.
Ubiquitous Language
Section titled “Ubiquitous Language”36 termos canônicos PT-BR. Source: Confluence 3813310465 (Versão Atual) + sessão de modeling 2026-05-28. Toda comunicação técnica e produto deve usar estes termos com a definição abaixo.
| Termo | Definição | Contexto / Origem |
|---|---|---|
| Order | Transação financeira no Bubble que origina uma OS na Omie. Pivot conectando evento Blueprintt ao faturamento. | Bubble · pivot |
| Event | Evento presencial gerenciado no Bubble. Determina datas de billing via event_date. | Bubble · Evento real |
| Customer | Empresa compradora no Bubble. CNPJ obrigatório (chave idempotência Omie). Razão social e email espelhados. | Bubble · cliente |
| OmieCompany | Empresa Omie integrada: AABC Organização de Eventos LTDA (CNPJ 50.162.682/0001-07). LNG fora do escopo. | Versão Atual · 07/05/2026 |
| OS | Ordem de Serviço Omie. Criada por ordens_servico.incluir. Pré-requisito para faturamento e NF-e. | Omie ERP |
| Projeto | Agrupador Omie por bubble_event_id. Idempotente — reutiliza se já existe para o evento. | Omie ERP |
| NFSe | NFS-e gerada por nfse.emitir. Terminal — cancelamento exige operação explícita. Registrada no Invoice Ledger. | Omie · documento fiscal |
| BillingTrigger | Intenção de quando faturar: immediate · pos_evento · custom_date. Passa pela Regra Dia 25. | Backend · enum |
| RegraDia25 | Se hoje > dia 25 e data desejada no mesmo mês, adia para dia 1 do próximo. Configurável via BillingCutoffPolicy. | utils/dia25.py |
| BillingDecision | Dataclass imutável de decide_billing(). Campos: status, scheduled_date, reason. Derivada a cada chamada. | Backend · engine |
| Rollover | Adiamento dia 25 → 1 do mês seguinte. Marca deferred=True + reason no action log. | compute_billing_date() |
| ConfirmacaoManual | Fluxo Petrobras-like — aguarda aprovação externa antes de faturar. Flag requires_manual_confirmation=true. | Cliente PJ corporate |
| Sync | Cria Customer + Projeto + OS na Omie a partir de Order Bubble. Idempotente por bubble_order_id. | OrderService.create_order() |
| EmitirNFSe | Emissão isolada de NF-e. Dois passos: ordens_servico.faturar + nfse.emitir. Idempotente via Invoice Ledger. | InvoiceService.emit_invoice() |
| IdempotencyKey | UUID por chamada HTTP. Tabela idempotency_cache. Mesmo body = resultado cacheado; body diferente = IdempotencyConflict. | Backend · contract |
| OmieIdMap | Mapeamento bidirecional Bubble↔Omie. Tabelas: omie_customer_map, omie_project_map, order_sync_record. | Backend · Postgres |
| InvoiceLedger | Tabela invoices append-only. Constraint: máximo 1 linha emitted por bubble_order_id. Replay retorna registro existente. | Backend · audit |
| ActionLog | Tabela action_log append-only. Cada chamada Omie/Bubble com payload, status, duração. Retention configurável. | Backend · audit |
| Bubble | Plataforma no-code Blueprintt. Fonte de verdade para Event, Customer, Order. Backend lê via Data API, escreve status via PATCH. | External · staging version-test |
| OmieERP | ERP SaaS via AsyncOmieClient. Sem sandbox global — cliente/OS reais. Aplicativo Demonstração = alternativa 7d. | External · AABC only |
| StatusPedido | Dimensão comercial. Enum: aguardando_pagamento · confirmado · cancelado. Independente de StatusFaturamento. | Confluence 3812950022 |
| StatusFaturamento | Dimensão fiscal/Omie. 9 valores: aguardando_pagamento · aguardando_confirmacao · bloqueado_dia25 · agendado · faturando · nf_emitida · nf_cancelada · erro_faturamento · faturamento_manual. | Confluence 3812950022 |
| Pagamento | Cobrança Pagar.me com charge_id + idempotency_key + amount_cents. TED/depósito sem charge_id. | Pagar.me · gateway |
| CartaDeCredito | Saldo de crédito por cancelamento de Pedido pago ou Participante. Transferível PF↔PJ. Uso total ou parcial. | Raiz separada |
| Vendedor | Usuário Blueprintt com flag is_vendedor=true. Vinculado ao Pedido (não ao ingresso). Alerta 7d sem liberação. | Backoffice · P11 aberto |
| Participante | Pessoa física no evento. Status: ativo · cancelado. Cancelar ajusta quantidade OS; gera CC proporcional se NF emitida. | Order · attendee |
| Evento | Sigla (ex: TFS26) → nome Projeto Omie. Nome completo → descrição OS/NFS-e. Cidade determina tipo de serviço. | Distinção crítica |
| TipoServicoOmie | (cidade × flag órgão público) → código Omie. SP/RJ mapeados. Outras cidades = seleção manual. Não hard-coded. | /servicos/listaservico/ · OMIE-1 |
| OrigemPedido | Canal: website (autoatendimento) · backoffice (operador assistido). HubSpot fora do escopo. | Versão Atual · dashboard |
| AguardandoConfirmacao | Pedido pago, faturamento suspenso aguardando autorização/empenho/número do cliente. Liberação via ApproveBillingHold. | Cliente PJ corporate |
| BloqueadoDia25 | Faturamento postergado pelo cutoff. PJ com regra_dia25_ativa=true. PF nunca cai. Override exige motivo + log. | Cliente PJ |
| FaturamentoManual | Operador registra Nº NF emitida fora da integração quando Omie quebra. Backend grava ManualBillingRecorded. | Bypass · fallback |
| ModalDecisaoFinanceira | Diálogo obrigatório ao cancelar Pedido pago. Opções: Carta de Crédito ou Reembolso. Emite RefundDecided. | Financeiro · UX |
| PagamentoFlexivel | Flag PJ — NF pode sair antes do recebimento. Versão Atual: NÃO determina mais roteamento AABC/LNG. Mantido como timing de NF. | Cliente PJ |
| BrasilAPI | API pública (brasilapi.com.br) — CNPJ via Receita Federal. Sem autenticação. Auto-preenche cadastro PJ. | External · gratuito |
| Pagarme | Gateway Stone. Cartão · PIX · Boleto (bloqueado se < 8d evento). Webhook charge.* com HMAC obrigatório. | External · gateway |
| HMAC | Validação X-Hub-Signature + PAGARME_WEBHOOK_SECRET. Assinatura inválida → HTTP 401, sem evento. | Webhook · segurança |
| RateLimitOmie | REDUNDANT = wait hint + 5s · HTTP 425 = ban 31 min. REDUNDANT classificado como OmieValidationError (não-retryable). | BLU-783 · pendente |