Alura > Cursos de Programação > Cursos de Quality Assurance > Conteúdos de Quality Assurance > Primeiras aulas do curso Qualidade de Software: escrevendo testes de maneira eficiente

Qualidade de Software: escrevendo testes de maneira eficiente

Princípios do teste de software - Apresentação: por que testar software?

Olá! Meu nome é Maurício Aniche, e serei o instrutor durante toda esta formação de testes na Alura.

Audiodescrição: Maurício é um homem branco, com cabelo curto castanho penteado em topete e olhos castanhos. Ele veste uma camisa verde e tem uma parede com quadros decorativos ao fundo.

Experiência e Publicações

Possuo mais de 20 anos de experiência na área de software, muitos deles dedicados à área de testes de qualidade. Escrevi o primeiro livro em português sobre TDD (Test Driven Development, ou Desenvolvimento Orientado a Testes), que também será abordado neste curso. Isso ocorreu em 2012. Mais recentemente, em 2021 e 2022, publiquei um livro sobre testes de software pela editora internacional Manning, intitulado Effective Software Testing (Testes de Software Eficazes). Muitas das lições que discutiremos ao longo deste curso são aprendizados que adquiri não apenas ao escrever esses livros, mas também ao observar como as ideias neles contidas evoluíram ao longo do tempo.

Motivação para a Qualidade de Software

Antes de começarmos, gostaria de compartilhar uma história sobre como me motivei a entender mais sobre testes e qualidade de software, e por que a qualidade se tornou tão importante em minha carreira. Trata-se de um incidente envolvendo um bug que ocorreu na República Dominicana.

Projeto de Automação de Postos de Gasolina

Por volta de 2005 ou 2006, eu trabalhava como consultor para uma empresa americana que desenvolvia hardwares conhecidos como POS (Point of Sale, ou Ponto de Venda), aqueles dispositivos onde inserimos o cartão de crédito e digitamos a senha. A ideia era usar esse hardware para automatizar postos de gasolina. Em vez de exigir um computador no posto, a lógica de controle seria implementada na maquininha de pagamento, que já era necessária para as transações.

Naquela época, eu já tinha algum conhecimento sobre essa plataforma de desenvolvimento embarcado, que envolvia programação em C. O dispositivo possuía um processador de 200 MHz, 1 ou 2 MB de memória RAM e 1 ou 2 MB de armazenamento, características bastante limitadas. Não era fácil encontrar pessoas com conhecimento nessa plataforma, mas eu já tinha alguma experiência. Formamos uma equipe, e eu era o líder de desenvolvimento, embora os títulos de carreira não fossem tão claros naquela época.

Primeira Experiência Internacional

Foi um momento importante para mim, pois estava no início da minha carreira e era a primeira vez que eu era responsável por um projeto de software. Minha intenção era criar o melhor projeto de software da história. Trabalhamos intensamente por cerca de 6 a 8 meses para desenvolver algo substancial. O deploy desse software exigia alterações físicas no posto de gasolina, pois precisávamos conectar as bombas ao nosso hardware. Naquele tempo, o conceito de continuous deployment (implantação contínua) ainda não era amplamente discutido.

Após codificarmos uma versão inicial, o primeiro piloto que a empresa encontrou foi em um posto de gasolina na República Dominicana.

O Incidente na República Dominicana

Na República Dominicana, tivemos uma experiência marcante. Viajamos para lá, animados com nossa primeira experiência internacional. Às 9 da manhã, iniciamos a operação do software, realizamos as instalações físicas e ficamos monitorando o funcionamento no posto. Tudo parecia estar indo bem: os clientes compravam combustível, os pagamentos eram processados e registrados no nosso back office, que operava no terminal. Até às 4 ou 5 da tarde, tudo estava funcionando perfeitamente. O proprietário do posto de gasolina comentou como o sistema economizaria tempo e dinheiro para ele e seus funcionários. Para comemorar, fomos à praia da República Dominicana.

No entanto, nem tudo foi perfeito. Por volta das 5 da manhã, recebi uma ligação de uma pessoa da equipe do posto informando que o software apresentou um problema, impedindo o abastecimento dos carros. O frentista tentava abastecer, mas a gasolina não saía da bomba. Esse comportamento foi programado no software para bloquear o abastecimento em caso de falha, evitando roubo de combustível. Com o coração acelerado, fui até o posto, desliguei o software, coloquei as bombas em modo manual e comecei a investigar o problema. Descobrimos que era um bug simples, resultado de um caso não tratado no sistema.

Lições Aprendidas e Importância dos Testes

Na época, realizávamos testes manuais, sem automação. Utilizávamos documentos de Word e planilhas de Excel com roteiros de teste, executados periodicamente por uma pessoa da equipe. Esses testes eram baseados em intuição, sem técnicas específicas. Essa experiência foi um marco na minha carreira, pois o software que desenvolvemos não funcionou por 24 horas sem apresentar um bug sério.

Acredito que muitos de nós já vivenciamos situações semelhantes, em que um bug causou a interrupção do funcionamento do software, possivelmente com impacto financeiro. Isso ressalta a importância da qualidade do software. Não queremos entregar um produto que não funcione, pois, dada sua importância para a sociedade, ele pode causar danos significativos.

Objetivos do Curso

Neste curso, nosso objetivo é explorar as diferentes facetas dos testes de software, não apenas a automação, que costuma ser o foco principal. Vamos abordar ferramentas, mas também como escrever bons testes. Saber quais testes escrever é crucial para identificar bugs de maneira correta, sistemática e eficiente.

Estamos prontos para essa jornada? Vamos em frente!

Princípios do teste de software - Escrevendo testes ao acaso

Algo que precisamos mudar na indústria de software, de maneira geral, é a ideia de deixar ao acaso a descoberta de bugs. Não devemos depender da sorte para encontrar um bug ao implementar uma funcionalidade. Precisamos aplicar métodos mais sistemáticos para explorar e identificar bugs. Isso deve ocorrer desde o início, na concepção e implementação, quando a pessoa desenvolvedora está programando as primeiras versões do código.

Estudo Observacional sobre Criação de Casos de Teste

Em 2020 e 2021, escrevemos um artigo científico enquanto ainda trabalhávamos para a universidade. O título do artigo era How Developers Engineer Test Cases in Observational Study (Como os desenvolvedores criam casos de teste em um estudo observacional).

How Developers Engineer Test Cases in Observational Study

A ideia desse artigo foi acompanhar um grupo de desenvolvedores criando testes para um determinado problema. Essas pessoas analisaram o requisito, observaram a implementação, implementaram testes, e nós analisamos os vídeos enquanto elas pensavam em voz alta. Conseguimos entender, aproximadamente, o que elas estavam tentando fazer.

Intuição e Informalidade na Criação de Testes

O artigo mencionado é bastante interessante e recomendamos a leitura. Um dos resultados que mais nos chamou a atenção foi que a maioria das pessoas desenvolvedoras segue, de certa forma, a intuição ao pensar no próximo caso de teste. Elas conhecem o requisito e a implementação, então param para refletir sobre qual seria o próximo caso de teste que faz sentido. Em seguida, implementam esse teste, verificam se o programa funciona ou não, e repetem o processo, pensando novamente sobre qual seria o próximo passo. Esse método é bastante informal.

Limitações da Abordagem Intuitiva em Problemas Complexos

Como será demonstrado mais adiante, essa abordagem funciona para problemas de complexidade limitada, onde conseguimos compreender o problema de maneira completa. No entanto, em problemas mais complexos, e nem precisam ser tão complicados assim, essa abordagem se torna mais difícil. Nesse ponto, começamos a depender do acaso ou da sorte para encontrar erros.

Foco na Descoberta Sistemática de Erros

Queremos mudar a ideia de que o mais importante é a ferramenta de teste, como saber JUnit, PyTest ou qualquer outra ferramenta utilizada na linguagem de programação. Quando falamos de teste de software, o foco é encontrar erros. Pretendemos mostrar técnicas que ajudarão de maneira sistemática a revelar e buscar por erros no código.

Conclusão: Abordagem Sistemática na Exploração de Testes

Portanto, vamos deixar de lado a ideia de depender da sorte e nos concentrar em encontrar testes, explorando o problema de maneira sistemática. Vamos em frente!

Princípios do teste de software - Escrever testes != Testar

Uma diferença que devemos ter em mente é a distinção entre escrever testes e testar. Essa foi, aliás, a principal crítica e a razão pela qual decidimos escrever o livro publicado pela Manning, "Effective Software Testing".

Ao observar a literatura de maneira geral e cursos disponíveis, percebemos que o foco é sempre muito voltado para ferramentas. Por exemplo, o JUnit e como utilizá-lo, explorando todas as suas funcionalidades. Da mesma forma, o Mockito, a ferramenta do mundo Java para criar mock, é amplamente discutido, destacando todas as suas funcionalidades.

Testes para Guiar o Desenvolvimento

Esses livros não apenas falam sobre ferramentas, mas também apresentam a ideia de escrever testes como uma forma de auxiliar na programação. Quando enfrentamos um problema muito complicado, escrevemos um pouco de teste, um pouco de implementação, talvez no estilo de TDD (Desenvolvimento Orientado por Testes), onde o teste é escrito antes. Esses testes estão mais presentes para nos ajudar a implementar o programa em que estamos trabalhando. Isso é o que chamamos de testes para guiar o desenvolvimento.

Foco em Testes para Testar

Os testes podem nos ajudar a pensar em pequenos passos, como discutido no capítulo de TDD e outros. Geralmente, muitos cursos focam em testes para guiar o desenvolvimento. Neste curso, queremos focar em testes para testar. Afinal, o que é teste de software? É a arte de explorar um programa em busca de bugs. Vamos mostrar também esse outro lado do mundo dos testes, que é o mais comum na academia.

Mentalidade de Testador

Lembremos que, ao escrever um teste automatizado, podemos estar fazendo isso por dois motivos. Um deles é para guiar o desenvolvimento, o que é muito útil e nos ajuda bastante. Nós fazemos isso frequentemente e apreciamos o TDD. O outro motivo é que, ao terminar, queremos procurar por bugs de verdade para garantir que, ao entregar uma funcionalidade, ela funcione corretamente e o usuário não fique insatisfeito.

Adotando a Mentalidade de Testador

Portanto, é importante mudar nossa perspectiva e adotar a mentalidade de testador, explorando o programa em busca de bugs. Mantenhamos essa separação em mente: escrever testes para guiar o desenvolvimento e escrever testes para encontrar bugs.

Sobre o curso Qualidade de Software: escrevendo testes de maneira eficiente

O curso Qualidade de Software: escrevendo testes de maneira eficiente possui 162 minutos de vídeos, em um total de 85 atividades. Gostou? Conheça nossos outros cursos de Quality Assurance em Programação, ou leia nossos artigos de Programação.

Matricule-se e comece a estudar com a gente hoje! Conheça outros tópicos abordados durante o curso:

Aprenda Quality Assurance acessando integralmente esse e outros cursos, comece hoje!

Conheça os Planos para Empresas