Arqueologia de Código Desvendando fósseis
Há milhares e milhares de anos, pouco antes dos dinossauros, foram encontrados os primeiros indícios de código legado.
O que não é um problema, já que todo código nasce legado, não é mesmo?! O código novo de hoje é o legado de amanhã =)
Passamos a maior parte do nosso tempo mantendo a nossa base de código e é interessante que esse processo não seja tão dolorido.
Ter uma cobertura de testes, não medida em números, mas uma cobertura de testes que você consiga mudar uma parte importante do seu código
e dormir a noite é um fator bem importante, senão o mais. Existem vários outros fatores, mas eu resolvi focar nessa ferida, e ela dói, principalmente em ambientes dinâmicos como no VivaReal.
Enfim, o mais importante nisso tudo é como vamos sobreviver, trabalhar felizes e com segurança nesse ambiente hostil.
Nosso case foi domar a Users-Api responsável por:
- autenticação
- cadastro
- favoritos
- buscas salvas
- integração com a responsys
- etc
E nosso problema começa aqui. Quais são as responsabilidades dessa api? Vamos começar a Arqueologia.
A api em questão tinha muitas responsabilidades, eu mesmo cheguei a mudar de opinião três vezes no mesmo dia a respeito da estratégia que iríamos adotar para conviver com isso. Vamos refazer tudo? Não vamos mexer? Vamos apenas migrar o código? Vamos dinamitar tudo? Vamos “Forkar”?
Baseado em alguns tombos, trancos e barrancos decidimos compartilhar a estratégia que achamos mais interessante e menos sofrida para extrair os serviços de autenticação e cadastro da UsersAPI.
Como tornar esse ambiente menos hostil ?
Já pensaram em escrever testes pra tudo que você conseguir? Foi isso que fizemos.
Galera, eu já ouvi muitos argumentos para não fazer isso, como:
- Precisamos ter um meio-termo;
- Escrever testes para tudo é too much;
- É difícil saber o que testar;
Na dúvida seja redundante. Mesmo que a princípio os testes sejam custosos para dar manutenção, pelo menos conseguimos garantir o comportamento da aplicação antes de sair “marretando” tudo.
Não refatore nada nesse momento, se possível escreva também testes para os bugs que forem encontrando durante essa jornada, vocês não tem idéia de como é difícil achar um bug e deixar de arrumar, dá coceira na mão e a vontade de corrigir é terrível, não arrume neste momento.
Como é um ambiente desconhecido não temos certeza se podemos adicionar mais um comportamento inesperado na aplicação.
Uma analogia muito boa dessa estratégia é:
Estamos construindo uma nova casa, sem derrubar a antiga e mantendo as pessoas dormindo dentro (sem poeira, rs)
Ouça os mais velhos
O Pedrito, que está no Vivareal praticamente desde o começo, foi uma figura muito importante para nós nessa passagem de conhecimento. Converse bastante com a galera que está há mais tempo na empresa para levantar o máximo de informações possíveis e diminuir a responsabilidade que esses caras têm. Estamos no mesmo barco, ninguém tem culpa de nada, e se assumimos o legado é responsabilidade de todos manter e melhorar. Legal documentar tudo isso também (em forma de testes). Ao invés de ser Hater é muito melhor entender o momento da empresa, entender as motivações e aprender com os erros, parar de mimimi e conviver com isso.
Não tenha medo (código não morde — by André)
A princípio pode parecer meio óbvio, eu mesmo torci o nariz a primeira vez que o André disse isso. Mas é pra isso que estamos aqui, temos todas as ferramentas para nos ajudar, não é várzea, não vamos sair quebrando tudo, mas ter medo de mexer por falta de testes não. "Tá com medinho? Escreve um teste!".
Existem vááááárias técnicas de refactoring baby-steps que nos ajudam a melhorar o design do código, organizar as coisas sem mudar o comportamento da aplicação.
Algumas técnicas de refactoring que usamos estão documentadas no Livro do Martin Fowler — Refactoring Improving the Design of Existing Code. Eu gosto muito deste livro, recomendo muito a leitura, vale um post só sobre técnicas de refactoring.
O Debug é seu amigo
Outra estratégia que nos ajudou foi "debuggar" bastante: subir a aplicação e executar todos os endpoints, executar o código mentalmente, entender o comportamento, e mais uma vez, documentar com testes.
No debug você encontra certos comportamentos que não conseguimos pegar simplesmente executando os caminhos felizes. É interessante forçar Exceptions em Runtime e valores null em variáveis que você considera importante, principalmente as que são alteradas em vários pontos do código.
Para concluir
No meio dessa jornada nós tomamos várias decisões precipitadas, como por exemplo começar uma aplicação nova sem entender perfeitamente o comportamento da anterior, e o principal, entender o que a aplicação antiga fazia a mais do que ela deveria. Erramos bastante em algumas decisões, porém aprendemos muito com esses erros e conseguimos reagir rápido e compartilhar com vocês.
Não comece uma aplicação nova sem conhecer a antiga. (Charlinho)