Padrões de Codificação¶
Versão: 1.0 Escopo: Padrões de Codificação, Integração Contínua (CI, sem CD), Variáveis de Ambiente (ENV), Linter, Formatter, Automação de Linter e Formatter, Convenção de Commits (Angular/Conventional Commits), Estrutura de Pastas (Clean Architecture + DDD) e Convenções de Nomenclatura.
Observação: Este documento é agnóstico quanto a linguagem de programação e ferramentas específicas. Ele define princípios e políticas que devem ser aplicados independentemente da stack escolhida pela equipe; a seleção das ferramentas concretas (linter, formatter, runner de CI, etc.) deve ser registrada à parte, em um documento de decisão técnica (ex.: ADR).
1. Objetivo¶
Este documento estabelece as práticas obrigatórias e recomendadas para a fase de construção de software do projeto, garantindo consistência, legibilidade, rastreabilidade e qualidade do código produzido pela equipe, independentemente de quem o escreva, da linguagem utilizada ou das ferramentas adotadas.
2. Padrões de Codificação¶
2.1 Princípios Gerais¶
- KISS (Keep It Simple, Stupid): prefira soluções simples a soluções "espertas".
- DRY (Don't Repeat Yourself): evite duplicação de lógica; extraia para funções/módulos reutilizáveis.
- YAGNI (You Aren't Gonna Need It): não implemente funcionalidades especulativas.
- SOLID: aplicável principalmente a código orientado a objetos, mas os princípios de responsabilidade única e baixo acoplamento valem para qualquer paradigma.
- Clean Code: funções pequenas, com um único propósito; evite efeitos colaterais ocultos.
- Domain-Driven Design (tático): a lógica de negócio deve residir no domínio (entidades, agregados, objetos de valor), nunca em camadas de infraestrutura ou apresentação.
2.2 Regras Práticas¶
| Regra | Diretriz |
|---|---|
| Tamanho de função/método | Pequeno, com responsabilidade única |
| Tamanho de arquivo/módulo | Dividir quando o arquivo passar a tratar mais de uma responsabilidade |
| Complexidade | Reduzir aninhamento e ramificações excessivas; extrair sub-rotinas quando a leitura ficar difícil |
| Comentários | Explicar o porquê, não o o quê (o código já expressa o quê) |
| Valores literais | Evitar números/strings "mágicos"; usar constantes ou objetos de configuração nomeados |
| Tratamento de erros | Nunca silenciar falhas sem tratamento ou registro explícito |
| Dependências não utilizadas | Não devem permanecer no código |
| Regras de negócio | Devem estar encapsuladas em entidades/agregados do domínio, não espalhadas em controllers ou serviços de infraestrutura |
3. Convenções de Nomenclatura¶
3.1 Princípios Gerais de Nomes¶
- Nomes devem ser descritivos e pronunciáveis, revelando intenção sem necessidade de comentário adicional.
- Evitar abreviações obscuras; preferir clareza a brevidade.
- Manter consistência de convenção de caixa (case) dentro de um mesmo contexto/projeto — a escolha específica (camelCase, snake_case, PascalCase etc.) depende das convenções idiomáticas da linguagem usada, mas deve ser única e documentada para o projeto.
- Nomes de elementos de domínio devem refletir a linguagem ubíqua (ubiquitous language) acordada com os especialistas de negócio, evitando termos puramente técnicos onde um termo de negócio já existe.
3.2 Categorias de Nomenclatura para o Back-end¶
| Elemento | Diretriz |
|---|---|
| Variáveis | Substantivos claros que expressam o dado armazenado |
| Funções/métodos | Verbos ou frases verbais que expressam a ação realizada |
| Classes/Tipos/Estruturas | Substantivos que representam o conceito ou entidade modelada |
| Entidades e agregados de domínio | Nome do conceito de negócio, sem sufixos técnicos (ex.: representar o conceito puro, não a sua persistência) |
| Objetos de valor | Substantivo que representa o valor imutável (ex.: representar o conceito, não um contêiner genérico) |
| Casos de uso/serviços de aplicação | Verbo + substantivo, expressando a intenção do usuário/ator (ex.: ação a ser executada) |
| Booleanos | Prefixos que indiquem condição (ex.: é, tem, pode, deve) |
| Manipuladores de evento | Prefixo que indique reação a um evento (ex.: "ao" / "quando") |
| Eventos de domínio | Verbo no particípio passado, expressando um fato já ocorrido |
| Constantes | Convenção distinta e reconhecível em relação a variáveis comuns |
| Arquivos/módulos | Nome alinhado ao conteúdo/responsabilidade principal do arquivo |
| Arquivos de teste | Sufixo ou prefixo que identifique claramente ser um teste, referenciando o alvo testado |
3.3 Nomenclatura de Branches¶
Padrão: tipo/descricao-curta-com-hifens
feature/checkout-payment-integration
fix/login-token-expiration
hotfix/prod-crash-order-service
chore/update-dependencies
release/v1.4.0
Tipos permitidos: feature, fix, hotfix, chore, refactor, docs, test, release.
4. Estrutura de Pastas do Back-end — Clean Architecture + DDD¶
A organização do código deve refletir a separação em camadas concêntricas proposta pela Clean Architecture, combinada aos padrões táticos do DDD dentro da camada de domínio e de aplicação. A regra de dependência é fundamental: camadas externas dependem de camadas internas, nunca o contrário, e o núcleo de domínio nunca depende de detalhes de infraestrutura.
Quando o sistema abrange múltiplos subdomínios, recomenda-se organizar primeiro por contexto delimitado (bounded context) e, dentro de cada contexto, aplicar a estrutura de camadas abaixo.
src/
<bounded-context>/ # (opcional) um por subdomínio/contexto delimitado
# em sistemas modulares; em sistemas menores,
# este nível pode ser omitido.
domain/ # Camada 1 — Enterprise Business Rules (núcleo)
entities/ # entidades com identidade e ciclo de vida
value-objects/ # objetos de valor imutáveis, sem identidade
aggregates/ # raízes de agregado e suas invariantes
domain-events/ # eventos que representam fatos do domínio
domain-services/ # regras de negócio que não pertencem a uma
# única entidade/agregado
repositories/ # interfaces/contratos de persistência
# (a implementação fica em infrastructure)
specifications/ # regras de consulta/validação reutilizáveis
exceptions/ # exceções específicas do domínio
application/ # Camada 2 — Application Business Rules
use-cases/ # orquestração de casos de uso específicos
commands/ # intenções de escrita/alteração de estado
queries/ # intenções de leitura
dtos/ # objetos de transferência de dados
ports/ # interfaces para serviços externos
# necessários à aplicação (ex.: notificação)
event-handlers/ # reação a eventos de domínio/integração
interface-adapters/ # Camada 3 — Interface Adapters
controllers/ # entrada de requisições/comandos externos
presenters/ # formatação da saída/resposta
gateways/ # adaptação de contratos externos
infrastructure/ # Camada 4 — Frameworks & Drivers
persistence/ # implementação concreta dos repositórios
mappers/ # tradução entre modelo de domínio e modelo de persistência
messaging/ # publicação/consumo de eventos externos
external-services/ # integrações com serviços de terceiros
web/ # camada de entrega (entrada/saída externa)
shared/ # Código transversal técnico
# (utilitários genéricos, tratamento de
# erros comum, tipos utilitários)
(utilitários, constantes, erros comuns)
config/ # Configuração de inicialização,
# composição/injeção de dependências
# entre as camadas e contextos.
tests/
unit/ # testes de domain e application isolados
integration/ # testes de interface-adapters e infrastructure
end-to-end/ # testes de fluxo completo do contexto
4.1 Regras de Dependência¶
domainnão conhece nenhuma outra camada nem frameworks externos.applicationconhece apenasdomain, orquestrando entidades/agregados para realizar casos de uso.interface-adaptersconheceapplicationedomain, nunca o contrário.infrastructureconhece todas as camadas internas (para implementá-las); nenhuma camada interna conheceinfrastructure.- A comunicação entre camadas internas e externas ocorre por meio de interfaces/contratos definidos nas camadas internas (
repositories,ports) e implementados nas camadas externas (infrastructure), respeitando a inversão de dependência. - Comunicação entre contextos delimitados diferentes deve ocorrer por meio de eventos de integração ou contratos explícitos, nunca por acesso direto ao domínio interno de outro contexto.
5. Linter (Análise Estática de Código)¶
5.1 Objetivo¶
Detectar automaticamente erros potenciais, código morto, violações de convenção e más práticas antes que o código seja integrado, reduzindo a dependência de revisão manual para problemas mecânicos.
5.3 Política de Uso¶
- A análise estática deve ser executada localmente, antes do commit, e obrigatoriamente na pipeline de CI.
- Nenhuma alteração pode ser integrada à branch principal com violações de regras classificadas como erro (bloqueante).
- O conjunto de regras deve ser versionado junto ao código-fonte, garantindo que toda a equipe utilize a mesma configuração.
6. Formatter (Formatação Automática)¶
6.1 Objetivo¶
Eliminar debates de estilo (indentação, espaçamento, uso de aspas, quebras de linha) automatizando a padronização visual do código, de forma que o formato nunca seja motivo de discussão em revisão de código.
6.2 Política de Uso¶
- A formatação deve ser executada localmente, antes do commit, e obrigatoriamente na pipeline de CI.
- Nenhuma alteração pode ser integrada à branch principal com violações de formatação classificadas como erro (bloqueante).
- O conjunto de formatação deve ser versionado junto ao código-fonte, garantindo que toda a equipe utilize a mesma configuração.
8. Convenção de Commits (Angular / Conventional Commits)¶
Formato obrigatório:
<tipo>(<escopo opcional>): <descrição curta no imperativo>
<corpo opcional explicando o quê e por quê>
<rodapé opcional: BREAKING CHANGE, referências a tarefas/issues>
8.1 Tipos Permitidos¶
| Tipo | Uso |
|---|---|
feat |
Nova funcionalidade |
fix |
Correção de bug |
docs |
Alterações somente em documentação |
style |
Formatação, sem alteração de lógica |
refactor |
Refatoração sem alterar comportamento externo |
perf |
Melhoria de performance |
test |
Adição/ajuste de testes |
build |
Alterações no sistema de build ou dependências |
ci |
Alterações em configuração/scripts de integração contínua |
chore |
Tarefas diversas que não afetam código-fonte ou testes |
revert |
Reversão de um commit anterior |
8.2 Exemplos¶
feat(auth): adicionar autenticação via OAuth2
fix(order): corrigir cálculo de frete para CEPs internacionais
refactor(user): extrair validação de e-mail para objeto de valor
docs(readme): atualizar instruções de instalação
feat(payment): adicionar suporte a novo meio de pagamento
BREAKING CHANGE: endpoint de pagamento agora exige o campo "method"
8.3 Regras¶
- Descrição no imperativo ("adicionar", não "adicionado" ou "adicionando").
- Sem ponto final na descrição curta.
- Primeira linha objetiva e concisa; detalhes adicionais vão no corpo do commit.
- A conformidade da mensagem com essa convenção deve ser validada automaticamente antes de o commit ser aceito.
9. Variáveis de Ambiente (ENV)¶
9.1 Princípios¶
- Nenhum arquivo contendo valores reais de configuração sensível (credenciais, chaves, segredos) deve ser versionado no controle de código-fonte.
- Deve existir um arquivo de exemplo, versionado, contendo todas as chaves de configuração esperadas, sem valores sensíveis preenchidos.
- A aplicação deve validar a presença e o formato das variáveis de ambiente necessárias em sua inicialização, falhando de forma explícita e imediata caso alguma esteja ausente ou inválida (fail-fast).
9.2 Exemplo de Arquivo de Referência¶
9.3 Boas Práticas¶
- Arquivos com valores reais devem estar listados no mecanismo de exclusão de versionamento do repositório.
- Deve haver separação clara de configuração por ambiente (desenvolvimento, teste, produção).
- Valores sensíveis de produção não devem, em hipótese alguma, transitar pelo repositório de código; devem ser gerenciados por um mecanismo seguro de gestão de segredos, externo ao versionamento.
10. Integração Contínua (CI) — sem CD¶
10.1 Objetivo¶
Garantir que toda alteração enviada ao repositório seja automaticamente validada — build, análise estática, formatação e testes — antes de ser integrada à branch principal. Este documento cobre apenas CI: não há deploy automatizado; a promoção para ambientes (homologação, produção) permanece manual/controlada e fora deste escopo.
10.2 Gatilhos¶
- A pipeline deve ser disparada a cada envio de alteração e a cada abertura/atualização de solicitação de integração (pull/merge request) direcionada às branches protegidas (ex.: principal e de desenvolvimento).
10.3 Etapas Recomendadas da Pipeline¶
- Obtenção do código-fonte na versão correspondente.
- Restauração/instalação de dependências.
- Execução da análise estática (linter).
- Verificação de conformidade de formatação.
- Execução de testes automatizados (unitários e de integração), incluindo validação das regras de dependência entre camadas quando possível.
- Execução do processo de build/empacotamento, garantindo que o artefato final é gerável.
- Emissão de relatório de cobertura de testes, quando aplicável.
10.4 Regras de Governança¶
- A integração de alterações às branches protegidas só deve ser permitida quando todas as etapas da pipeline forem concluídas com sucesso.
- Deve ser exigida ao menos uma aprovação de revisão de código antes da integração, independentemente do resultado da pipeline.
- Falhas na pipeline devem bloquear a integração de forma automática, sem possibilidade de contorno manual não documentado.