Você acredita no seu código? Testes, build e integração contínua

Como você faz para saber que seu software funcionou?

É impressionante perceber que estamos quase na primavera de 2006 e é tão fácil encontrar aplicações e bibliotecas sem uma única linha de código de teste.

Os problemas que surgem são os clássicos da época do cartão perfurado:

  • alterou uma coisa aqui, resultou em um bug ali
  • o responsável vai lançar um update novo do projeto mas não faz idéia se o que foi alterado está funcionando ou não
  • o “testador” verifica manualmente aquilo que foi alterado, mas acaba esquecendo de testar alguns itens
  • um bug gravíssimo foi encontrado portanto o gerente lança o projeto no meio de uma modificação. Resultado: código que não foi testado está em produção
  • conversa entre o usuário final e o desenvolvedor: usuário: Isso aqui não está funcionando, programador: na minha máquina funcionou

A última frase, por mais natural que pareça, é uma das coisas mais estranhas que existem na área. O programador foi contratado para o sistema funcionar em determinada arquitetura/so/etc, portanto enquanto o sistema não funcionar na máquina do seu cliente, não faz sentido dizer que ela funciona.

Hoje em dia trabalhamos com o desenvolvimento voltados a testes – quase todos os tipos deles – automatizados. Tanto na Caelum, quanto nos projetos open source que participamos. No XStream, por exemplo, nada pode ser comitado sem testes, e se for um novo recurso você também precisa comitar um pequeno tutorial, para que nada passe como “feature avançada não documentada”.

Isto é, usando ferramentas como o JUnit, Cargo, FIT e Fitnesse além do controlador VRaptor, o servidor Jetty, a biblioteca Hibernate e de bancos como o HSQLDB e o Derby, é possível criar diversos ambientes de teste, produzindo os seguintes resultados:

Integração contínua

  • Suas alterações são feitas e você efetua o commit para o controle de versão (cvs, subversion etc)
  • O sistema de integração contínua percebe o commit e, cerca de 1 minuto depois, efetua o processo de build
  • Ferramentas: BeetleJuice, CruiseControl ou até mesmo o TeamCity

Processo de build

  1. Baixa a última versão do controle de versão (checkout)
  2. Compila o código fonte
  3. Executa os testes unitários, verificando que suas classes funcionam sozinhas como deveriam, usando JUnit
  4. Levanta um servidor web embutido (jetty) usando o cargo
  5. Levanta um banco de dados embutido (hsqldb)
  6. Executa os testes de integração e aceite, onde o código html e os cliques que o cliente fazem são simulados, usando JUnit e VRapor
  7. Levanta um servidor web igual ao de produção (websphere, por exemplo), usando o cargo
  8. Levanta um banco de dados igual ao de produção (oracle, por exemplo)
  9. Executa os testes de integração e aceite na réplica da produção

Se algum desses passos falhar, o sistema notifica o time e o responsavel por quebrar a integração. Note que a integração é continua, isto é, ela percebe os commits, e não espaçada – sendo rodada uma vez por dia.

Nem sempre atingimos 100% de code coverage, dado que podemos extrair usando o Clover Report, mas saber que 70% ou mais do seu código foi testado e funciona como antigamente ajuda a efetuar modificações no seu código.

Sinceramente, não dá para confiar mais em código não testado automaticamente. Quais são as garantias que você tem que amanhã, aquilo que funcionava hoje não deixará de funcionar?

Lembro de quando o Carlos Villela falava de fazer todas essas etapas de teste e build “complexos” e achava coisa a mais. É impressionante como após fazer isso uma vez você não consegue mais viver sem ela.

Para aqueles que se motivaram a testar, divirtam-se, para os outros, boa sorte.

9 Comentários

  1. Fabio Kung 09/09/2006 at 17:02 #

    Pense só como deve ser difícil fazer um chip com milhões de transistores que funcione de forma adequada!

    A engenharia de hardware está anos-luz na frente da engenharia de software, na minha opinião. É difícil de ver software que sequer funcione direito!

    Dá para sequer achar que o processo de desenvolvimento de um processador ocorra sem testes contínuos? Existem até os pinos de depuração…

    Pense num sistema que calcule a dosagem de medicamento para pacientes. Dá para arriscar a vida de pessoas em “Acho que calcula direito”, ou “Funcionou direito na minha máquina” ? É inaceitável uma coisa dessas…

    Não vejo como ter software com qualidade sem testes automatizados!

  2. Fernando Boaglio 11/09/2006 at 10:35 #

    Não dá pra fazer uma comparação nua e crua com a Engenharia de Hardware, pois não temos recém formados ou pessoas de outras áreas criando processadores.
    Além disso testar um processador é um processo muito exato e preciso, o que é bem diferente de testar o funcionamento de um software e simular todas as situações (algumas até bizarras) que um usuário pode fazer.
    Pergunta ao Guilherme: eu consigo integrar todos esses frameworks que vc usa para testes no Maven2?

  3. ASOBrasil 11/09/2006 at 11:11 #

    Guilherme,

    Concordo plenamente com seu ponto de vista! Agora uma pergunta. Será que o problema também não está na forma de como os softwares são desenvolvidos na maioria das empresa? Ou seja, a passos de tartaruga no começo do projeto, pois faz-se muita documentação que o desenvolvedor nem acaba usando e fica a correria para o final do projeto! Trabalhei em uma empresa onde contrataram um cara para cuidar da parte de testes e validar o código feito pelos desenvolvedores; no final do projeto, até o cara estava desenvolvendo de tão atrasado que estava! E justamente porque perdeu-se tempo demais na fase da análise! Reuniões/documentação, reuniões/documentação e desenvolvimento que é bom nada! É claro também que boa parte da culpa é do desenvolvedor que não sabe ou tem preguiça de criar testes automatizados e acaba não impondo essa condição para melhoria do seu próprio trabalho!

  4. Guilherme Silveira 12/09/2006 at 10:56 #

    Boaglio, boa parte do que comentei integra com Maven 2. So o Cargo e o FIT que eu apanho. O Cargo dá para dar um jeito, o FIT não consegui totalmente, ainda. Todo o resto tem exemplos de como fazer etc.

    O problema está em diversos lugares mesmo… desde a empresa pedir demais de pessoas com pouca experiência até o volume enorme de programadores no mercado. Além disso, um desenvolvedor deve saber quando colocar uma prática nova em jogo na empresa, e a empresa semi-aberta a novas idéias.

  5. Fabio Kung 13/09/2006 at 09:07 #

    Claro que comparar com os processos usados na fabricação de hardware é um pouco difícil, mas é possível sim.

    Boaglio, é justamente o fato de não ter pessoas recém-formadas fabricando processadores que confirma o fato de que o desenvolvimento de hardware está bem mais avançado que o desenvolvimento de software. De fato, a engenharia de sofware é bem mais nova, mas isso não pode ser desculpa!

    Criar um processador não é um processo exato e preciso: também está sujeito a erros. A diferença aí é justamente a preocupação com a qualidade. Não acho que seja muito diferente de se preocupar com a qualidade do software. É difícil esgotar todas as possibilidades de teste de um software, assim como também é difícil esgotar as possibilidades de teste em um processador.

    E olha que eu ainda nem comentei que no desenvolvimento de hardware também há bastante software (os microprogramas, por exemplo).

  6. Sandro Santos Guimarães 15/09/2006 at 09:03 #

    Guilherme,
    Achei muito legal o arquivo, e até já li muita coisa sobre teste mas nada que fosse tão completo.
    O que vc acha de um tutorial publicado na MJ sobre isso, mas dessa maneira completo, ou pelo menos no GUJ. 🙂
    Parabéns!

  7. Fabio Kung 15/09/2006 at 13:58 #

    Outra dica de ferramenta que verifica a cobertura do código por testes (code-coverage): Cobertura.

    Tenho testado e estou bem satisfeito! A vantagem sobre o Clover é que o Cobertura tem a licensa Apache 2.0, podendo ser usado em projetos comerciais (o Clover só é gratuito para projetos de software livre).

    Outro ponto importante é que o Cobertura integra bem (e fácil) com o maven 2!

  8. Lucimara 06/06/2008 at 18:59 #

    Sao varios os motivos para nao termos software com qualidade. E isso vai desde uma analise mal elaborada ate a programacao. Muitos programadores, infelizmente, nao realizam testes unitarios. Algumas empresas tambem nao aplicam uma metodologia agil de desenvolvimento de software, onde a equipe de programadores interajam, sabendo o q um e outro esta desenvolvendo. Enfim… sao varios os motivos e cabe a empresa e a equipe de desenvolvimento tomarem todas as providencias para que seja desenvolvido sistemas que realizam aquilo q o cliente quiz.
    Quanto ao artigo, muito bom, excelente.

  9. José Carlos 13/11/2012 at 10:36 #

    Idependente da complexidade do dos sistemas ou dos produtos que desenvolvemos é preciso ter gestão devidamente capacitada para avaliar se temos os recursos que precisamos, definir metodologia que cubra todos os processos de desenvolvimento, proseguir melhorando os processos e entregar apenas o que já foi previamente testado.

Deixe uma resposta