Convention over configuration: o princípio que reduz decisões desnecessárias

1. O que é Convention over Configuration (CoC)?

Convention over Configuration (CoC) é um princípio de design de software que preconiza a adoção de convenções padrão para reduzir a quantidade de decisões que um desenvolvedor precisa tomar ao configurar um sistema. O termo foi popularizado por David Heinemeier Hansson, criador do Ruby on Rails, que publicou o framework em 2004 com a premissa de que "você não precisa configurar algo que já tem um comportamento esperado".

A diferença fundamental entre CoC e configuração explícita está na abordagem: enquanto a configuração explícita exige que o desenvolvedor declare cada detalhe do funcionamento do sistema, o CoC assume comportamentos padrão baseados em convenções amplamente aceitas. Por exemplo, em vez de configurar manualmente que o arquivo usuarios_controller.rb deve responder a requisições HTTP para a rota /usuarios, o framework já assume essa relação pela simples nomenclatura do arquivo.

Esse princípio reduz significativamente a carga cognitiva porque elimina decisões triviais — como "qual nome dar a esta rota?" ou "onde guardar este arquivo?" — permitindo que o desenvolvedor se concentre no que realmente importa: a lógica de negócio do sistema.

2. Como CoC elimina decisões desnecessárias no dia a dia

A eliminação de decisões acontece de forma prática em várias camadas do desenvolvimento. A nomeação de arquivos e pastas é o exemplo mais clássico. Em frameworks como Rails, a estrutura de diretórios já define o propósito de cada arquivo:

app/
  controllers/
    usuarios_controller.rb    # Automaticamente mapeado para /usuarios
  models/
    usuario.rb                # Automaticamente ligado à tabela 'usuarios'
  views/
    usuarios/
      index.html.erb          # Automaticamente renderizado na action index

No banco de dados, a convenção vai além: um modelo chamado Usuario automaticamente espera uma tabela chamada usuarios (pluralizado). Um campo usuario_id é automaticamente interpretado como chave estrangeira para a tabela usuarios.

Exemplo prático em texto: imagine criar um CRUD completo sem configurar cada rota. Em um framework com CoC, você apenas cria o modelo, o controller e a view seguindo as convenções de nomenclatura. O framework automaticamente expõe as rotas RESTful (index, show, new, create, edit, update, destroy) sem que você escreva uma única linha de configuração de rota.

# Apenas com esses arquivos, o CRUD completo funciona
# app/models/produto.rb
# app/controllers/produtos_controller.rb
# app/views/produtos/index.html.erb
# app/views/produtos/show.html.erb
# app/views/produtos/new.html.erb
# app/views/produtos/edit.html.erb

3. Vantagens concretas de adotar CoC em projetos

A redução de boilerplate é a vantagem mais imediata. Projetos que seguem convenções eliminam centenas de linhas de configuração manual. Em um estudo informal, estima-se que Rails reduz em até 70% o código de configuração comparado a frameworks Java tradicionais da mesma época.

O onboarding de novos desenvolvedores acelera drasticamente. Quando todos os projetos seguem as mesmas convenções, um desenvolvedor que chega a uma nova equipe já sabe onde encontrar os controllers, como nomear migrations e como estruturar testes. A curva de aprendizado passa a ser sobre o domínio do negócio, não sobre a arquitetura do projeto.

A consistência entre projetos é outro benefício crucial. Equipes que adotam CoC criam projetos que parecem ter sido escritos pela mesma pessoa, mesmo com dezenas de desenvolvedores ao longo dos anos. Isso reduz drasticamente o atrito em manutenções e transferências de código.

4. Quando a convenção se torna um problema (limitações)

Nem tudo são flores. Projetos com requisitos muito específicos frequentemente encontram resistência nas convenções. Se você precisa de uma rota não RESTful ou de uma estrutura de banco de dados que não segue o padrão de nomenclatura, o CoC pode se tornar um obstáculo.

A dificuldade de depuração é outro ponto crítico. Quando uma convenção quebra silenciosamente — por exemplo, um arquivo nomeado incorretamente — o desenvolvedor pode gastar horas tentando entender por que o sistema não está se comportando como esperado. A mágica do "funciona sem configuração" pode se transformar em "não funciona e não sei por quê".

O risco de "caixa preta" é talvez o mais perigoso. Desenvolvedores que nunca precisam configurar nada podem não entender o que está acontecendo por baixo dos panos. Quando surge um problema que exige conhecimento profundo do framework, esses profissionais ficam perdidos.

5. CoC vs Configuration: como equilibrar os dois mundos

A boa notícia é que frameworks modernos permitem sobrescrita de convenções. Rails, Spring Boot e Django oferecem mecanismos para configurar exceções quando necessário, sem abandonar os benefícios das convenções padrão.

A estratégia recomendada é: comece com convenção, configure apenas quando necessário. Isso mantém a produtividade inicial e só adiciona complexidade onde realmente faz sentido.

Exemplo em texto de sobrescrita de convenção em um ORM:

# Por convenção, o modelo 'Cliente' espera a tabela 'clientes'
# Mas podemos sobrescrever:
class Cliente < ApplicationRecord
  self.table_name = "clientes_antigos"  # Tabela legada
  self.primary_key = "codigo_cliente"   # Chave primária não padrão
end

6. Relação com outros princípios e padrões da lista

O CoC dialoga diretamente com vários princípios da lista de 1200 temas. Em relação ao SOLID, especialmente o Open/Closed Principle, as convenções podem tanto apoiar quanto violar o princípio. Convenções bem definidas permitem estender comportamentos sem modificar código existente (aberto para extensão), mas podem ser difíceis de alterar (fechado para modificação) quando o requisito foge do padrão.

Padrões como Singleton e Factory se beneficiam enormemente de convenções de criação. Frameworks que seguem CoC frequentemente implementam factories automáticas baseadas em convenções de nomenclatura, eliminando a necessidade de escrever código de criação manualmente.

No Code Review, convenções reduzem discussões sobre estilo e estrutura. Em vez de debater se o controller deve se chamar UsuariosController ou UsuarioController, a equipe simplesmente segue a convenção estabelecida. O foco da revisão volta para a lógica de negócio e a qualidade do código.

7. Dicas práticas para implementar CoC na sua equipe

Para implementar CoC efetivamente, comece definindo convenções internas antes do projeto começar. Documente nomes de pastas, padrões de commits, nomenclatura de branches e estrutura de arquivos. Essa documentação deve ser acessível e revisada periodicamente.

Documente exceções de forma explícita. Quando uma convenção for quebrada por necessidade técnica, registre o motivo e a data da decisão. Isso evita que futuros desenvolvedores tentem "corrigir" algo que foi intencionalmente diferente.

Utilize ferramentas que automatizam a verificação de convenções. Linters como RuboCop para Ruby, ESLint para JavaScript e ferramentas de geração de código (generators) ajudam a manter a consistência sem esforço manual.

# Exemplo de configuração de linter para convenções
# .rubocop.yml
Naming/FileName:
  EnforcedStyle: snake_case
  Exclude:
    - 'db/migrate/*.rb'  # Migrations têm convenção própria

8. Conclusão: CoC como filosofia de design de software

Convention over Configuration não é sobre preguiça ou falta de controle — é sobre inteligência aplicada ao design de software. Ao reduzir decisões desnecessárias, liberamos energia mental para resolver problemas que realmente importam.

Os benefícios são claros: menos código, onboarding mais rápido, consistência entre projetos e maior produtividade. As limitações existem, mas podem ser gerenciadas com sobrescritas bem documentadas e conhecimento profundo dos frameworks.

CoC nos ensina que boas decisões de design não são sobre ter mais opções, mas sobre eliminar as opções que não agregam valor. É uma filosofia que transforma a maneira como pensamos sobre arquitetura, produtividade e, acima de tudo, sobre como criar software que realmente funciona.

Referências