Fundação/Modelo de Dados
Core #3 · Data Conventions
Modelo de Dados
O "código civil" das tabelas — o que garante que 5 pilares construídos ao longo de meses pareçam um sistema só.
A
As convenções
| Regra | Convenção |
|---|---|
| IDs | UUIDv7 (time-ordered) + ID público com prefixo — cont_7f3a… |
| Temporais | Sempre timestamptz em UTC; conversão de fuso só na apresentação |
| Soft-delete | deleted_at universal; archived_at ≠ delete; hard-delete só p/ LGPD |
| Dinheiro | bigint em unidades menores + moeda — nunca float |
| Enums | text + CHECK (não pg enum, doloroso de alterar) |
| JSONB | Só p/ settings/meta/custom; dado consultável = coluna |
| Concorrência | Coluna version p/ optimistic lock |
| Alto volume | Particionamento por tempo em audit/event/métricas |
| Custom fields | custom_field_def tipado + valores em custom jsonb (GIN) |
| Migrations | Drizzle, forward-only, expand-contract p/ zero-downtime |
B
Base Table Template
A assinatura que toda tabela de negócio herda.
-- lei do Core: workspace_id + RLS em toda tabela de negócio CREATE TABLE <entity> ( id uuid PRIMARY KEY DEFAULT uuidv7(), -- time-ordered workspace_id uuid NOT NULL REFERENCES workspace(id), client_id uuid REFERENCES client(id), -- quando aplicável -- … colunas de negócio … custom jsonb NOT NULL DEFAULT '{}', -- custom fields tipados meta jsonb NOT NULL DEFAULT '{}', version int NOT NULL DEFAULT 1, -- optimistic lock created_at timestamptz NOT NULL DEFAULT now(), -- UTC updated_at timestamptz NOT NULL DEFAULT now(), deleted_at timestamptz -- soft-delete ); ALTER TABLE <entity> ENABLE ROW LEVEL SECURITY; CREATE POLICY tenant_isolation ON <entity> USING ( workspace_id = current_setting('app.workspace_id')::uuid ); CREATE INDEX ON <entity> (workspace_id) WHERE deleted_at IS NULL;
Os módulos só acrescentam suas colunas de negócio. Veja o modelo do CRM como primeiro exemplo aplicado.