Desenvolvimento Orientado a Testes - Revista Engenharia de Software Magazine 47
Este artigo irá abordar as motivações e vantagens de se utilizar uma técnica de desenvolvimento orientada a testes, o TDD, e também descrever cada passo de sua utilização.
Este artigo irá abordar as motivações e vantagens de se utilizar uma técnica de desenvolvimento orientada a testes, o TDD, e também descrever cada passo de sua utilização, tais como o conceito de vermelho/verde/refatore, baby steps e TDD como prática de design afim de fundamentar a implementação de algumas regras de negócio. Neste contexto, este artigo tem a intenção de apresentar TDD e guiar os primeiros passos dos desenvolvedores que desejam melhorar a forma como escrevem código e minimizar as falhas de software através do desenvolvimento orientado a testes.
O tema é útil para desenvolvedores e gerentes, seja de metodologias ágeis ou não, para melhorar o produto final do desenvolvimento, através de uma técnica que alia testes com qualidade de código, e que queriam introduzir esta técnica em suas equipes de desenvolvimento.
Com a evolução dos sistemas e o aumento da complexidade dos requisitos, se torna mais complicado identificar e corrigir falhas. O TDD é uma técnica de desenvolvimento que permite um feedback mais rápido da aplicação em desenvolvimento. Neste artigo será apresentado o TDD em sua forma mais simples. Seus conceitos, vantagens, motivações serão discutidos para, ao final, exemplificar tudo que foi dito em uma pequena implementação demonstrando todo o processo de desenvolvimento.
Desde o início do desenvolvimento de software até os dias atuais é notável a grande mudança na forma como aplicações são desenvolvidas. Com o crescimento dos sistemas e a complexidade dos requisitos aumentando, foi ficando cada vez mais complicado identificar e corrigir falhas de código (ou até mesmo falhas nos requisitos) rapidamente, sem perdas para cliente e empresa.
Metodologias foram criadas justamente para tentar diminuir esta quantidade de erros que existiam. Foram adotadas metodologias em cascata, espiral e metodologias ágeis, dentre outras, todas com suas qualidades e defeitos, com o único objetivo de deixar o desenvolvimento mais confiável, mais correto. Uma das técnicas utilizadas nas metodologias ágeis é o Test Driven Development (TDD).
O TDD diz que se deve mudar a forma de programar. Ao invés de escrever o código e depois testar, no TDD deve-se testar antes de escrever.
O benefício do TDD foi comprovado em diversos estudos. Não só as aplicações possuíam menos defeitos, como o design do código era melhor do que as aplicações que não o utilizavam. TDD não é uma técnica exclusiva das metodologias ágeis de desenvolvimento. Trata-se de um método de desenvolvimento singular que pode ser utilizado tanto em metodologias ágeis como em metodologias que utilizam ciclos de vida em cascata ou espiral, só que ao invés de se aplicar em estórias, serão aplicados no desenvolvimento dos requisitos mapeados.
Normalmente, durante o ciclo de desenvolvimento tradicional, os profissionais tendem a especificar uma funcionalidade e implementá-la para que depois, lá no fim, esta funcionalidade seja testada (isso quando são testadas).
Essa forma de desenvolvimento já se mostrou bastante ineficiente. O número de falhas no software é altíssimo. O tempo depurando a aplicação é muito superior ao de desenvolvimento em si, e com essa perda de tempo, junto com as próprias falhas de software, acaba se perdendo muito dinheiro. O que ainda se tornou pior é que software virou sinônimo de bug. Uma aplicação possuir erros se tornou uma coisa normal.
Agora, imagine se a construção de carros fosse parecida com o desenvolvimento de software. Ou mesmo um procedimento cirúrgico fosse feito da mesma maneira como é desenvolvido um software.
Foi nesse ponto que, através de estudos e acompanhamentos de outros processos, foi proposto o TDD como forma de minimizar as tantas falhas de software e aumentar a qualidade do código-fonte produzido.
A filosofia do TDD é simples: código limpo e que funciona. Mas como chegar a este ponto?
O desenvolvimento orientado a testes segue um mantra no qual a premissa básica é: teste antes de implementar. Com esta simples inversão de etapas durante o desenvolvimento já se consegue grandes vantagens, tais como:
● Trazer o teste para mais perto do desenvolvedor (onde as regras de negócio estão sendo criadas ou implementadas);
● Documentar o código através de testes durante o desenvolvimento;
● Testes para funcionalidades desenvolvidas;
● Melhoria na qualidade do código. Código fácil de testar é código bem feito.
O mantra vermelho/verde/refatore é a base para se utilizar o TDD. Ele descreve o ciclo de tarefas que devem ser feitas ao implementar uma funcionalidade. Para iniciar o desenvolvimento com TDD, antes mesmo de escrever qualquer linha de código, primeiro será escrito um código que teste a funcionalidade.
Com o teste escrito, o mesmo é executado e falha, uma vez que a funcionalidade ainda não foi construída. Este passo parece não ser necessário (claro que o teste irá falhar, não se tem código ainda), porém é bastante importante e será abordado mais a frente.
Assim que o teste falhou, deve-se para fazer as modificações necessárias para ver o teste passar. Lembrando sempre, falha é progresso.
Depois de escrever o código para fazer o teste passar, deve-se executar o teste e verificar se está passando.
Um ponto importante neste momento (codificação) é nunca perder o foco do teste. Só se deve implementar a solução mais simples que faça o teste passar - este pequeno passo é conhecido como baby step.
Com o teste aprovado, é hora de refatorar o código escrito, sempre lembrando que código de teste também é código-fonte.
Este é o ciclo do TDD. O conceito é bastante simples, mas implementar é um pouco mais complicado devido à quebra de paradigma do padrão tradicional.
Durante o desenvolvimento, muitas pessoas têm dificuldade em perceber o que testar, ou não vêem os testes falharem, ou ainda não executam todos os testes. Isso será abordado adiante.
Uma das dúvidas mais comuns no desenvolvimento utilizando TDD é o que testar. Como o teste é a primeira coisa que será escrito, precisa-se conhecer bem a funcionalidade que será implementada.
O ideal e recomendado é, antes de iniciar a implementação da funcionalidade, escrever tudo que a funcionalidade deve fazer e quais as regras que se pretende testar. Desta forma se conhece melhor o que será testado/desenvolvido e evita-se perder o foco durante o teste, que é outro grande problema durante o ciclo do TDD.
Ao escrever o teste, deve-se escrever o menor teste possível que descreva uma funcionalidade, mantendo-se no simples.
É interessante, no começo, escrever testes para pequenas funcionalidades. A medida que vai se habituando com o ritmo do TDD, pode-se evoluir para escrever testes para funcionalidades mais complexas.
Ver o teste falhar
O primeiro teste a ser escrito sempre exibirá erros de compilação, normalmente referentes a classes e métodos que não existam, o que fará o teste não compilar.
Após sanar todos os problemas de compilação (somente deve-se programar o necessário para os problemas de compilação serem resolvidos, não se deve começar a programar a resolução do problema ainda) execute todos os testes escritos e os veja falhar.
É importante ver o teste escrito falhar pois através deste processo, terá a certeza de que o comportamento do teste é o esperado: falha.
Esse processo serve para impedir que se escreva testes em que são esperadas falhas e mesmo assim eles passem. Isto pode ser fruto de uma validação de regra de negócio feita incorretamente, o que pode gerar grandes problemas em um ambiente de produção.