ADR 0003 — Monorepo da empresa, e não um repositório por produto
Status: canônico · Escopo: Onde novos produtos nascem e como as responsabilidades são separadas · Atualizado em: 2026-08-10
Registra por que os próximos produtos da Tactflow nascem dentro de um repositório só, por que não haverá repositório-modelo, e o que separa responsabilidade de fato. Existe porque a pergunta foi feita ao planejar CRM interno, front-end do usuário e o produto de leitura de documentos.
Contexto
Seção intitulada “Contexto”Hoje são dois repositórios: voltron (quatro apps, dois pacotes, dois Workers
publicáveis — ver ADR 0002) e tactflow-site (o site de
marketing, Astro em Cloudflare Pages). Três produtos estão previstos: CRM interno, front-end do
usuário e leitura de documentos.
O custo de manter dois repositórios já é observável, não é hipótese:
src/scripts/talk-api.ts, no site, copia à mão o contrato do backend — mesmos campos, mesmos setores, mesma derivação da perda. A divergência entre as duas cópias é considerada provável a ponto de o servidor re-derivar o número e responder 422 quando as contas não batem. Isso é uma guarda contra um problema que só existe porque são dois repositórios.- Renomear o hostname de
chat.tactflow.ioparaapi.tactflow.io(#65) exigiu dois PRs coordenados, com ordem de deploy pensada à mão para não quebrar quem estivesse no meio do funil. Com quatro repositórios, seria quatro.
Decisão
Seção intitulada “Decisão”Um repositório da empresa — tactflow-platform — com vários publicáveis dentro. Não um
repositório por produto, não um serviço único.
tactflow-platform/ apps/ api-worker · site · crm · app · docs-ai packages/ contracts · db · uiNão haverá repositório-modelo. O que mantém os projetos parecidos é código compartilhado de
verdade (packages/) mais a regra de camadas cobrada pelo dependency-cruiser. Um modelo copiado
desalinha no primeiro projeto que diverge, e aí existem duas convenções em vez de uma.
Separar responsabilidade é a regra de camadas, não a fronteira de repositório. Repositório separado dá a sensação de fronteira sem cobrar nada; a regra de camadas reprova o build.
Consequências
Seção intitulada “Consequências”Fica mais fácil: contrato existe uma vez e é importado, não copiado; mudança que atravessa produtos cabe num PR revisável; uma CI, um lint, uma versão de cada dependência — o que importa para uma pessoa só mantendo tudo.
Fica mais difícil: o repositório cresce e o git log mistura produtos; alguém que só cuida do
CRM clona o que não usa; a regra de camadas precisa ser mantida viva, senão vira decoração.
Passa a ser proibido: criar repositório novo para produto novo da Tactflow sem revisar esta
ADR. E copiar contrato entre apps em vez de extrair para packages/.
O que isto não resolve: um deploy continua passando por cima de todos os publicáveis do repositório. É aceitável enquanto os clientes são testers. O gatilho para separar publicáveis está escrito na #65 — existir cliente pagante cuja ligação não pode ser arriscada por um deploy de marketing — e é gatilho de publicável, não de repositório.
Alternativas descartadas
Seção intitulada “Alternativas descartadas”| Alternativa | Por que perdeu |
|---|---|
| Um repositório por produto | Dá fronteira de verdade e deploys independentes, mas cobra contrato versionado entre repositórios, cliente gerado e mudança atravessada em N PRs coordenados. Os dois repositórios de hoje já pagam esse preço — a cópia manual do contrato e os dois PRs da renomeação são a fatura. Multiplicar por cinco produtos com um desenvolvedor é trocar acoplamento de deploy por acoplamento de calendário. |
| Repositório-modelo (template) | Resolve o primeiro dia e nada depois. No instante em que o segundo projeto diverge, passam a existir duas convenções e nenhuma ferramenta reclamando. Código compartilhado e regra cobrada no CI fazem o que o modelo promete e continuam fazendo no sexto mês. |
| Um serviço único | Simplifica o deploy e destrói o isolamento: o produto de documentos derrubaria a ligação de voz. Publicáveis separados dentro de um repositório dão o isolamento sem o custo de coordenação. |
Onde continuar
Seção intitulada “Onde continuar”- Ferramenta de monorepo e enforcement:
ADR 0002 - Regras de boundary e o self-test:
ARCHITECTURE.md - As três camadas de nome e o gatilho para separar publicáveis: issue #65