Baixe o app para aproveitar ainda mais
Prévia do material em texto
Unidade III – Testes de Validação 13 – Métodos Estruturados Unidade III Avaliação de Software Prof. Ulisses Sperle Graça Abr/2013 2 Os métodos de verificação vistos anteriormente baseiam-se em técnicas de testes estáticos para avaliar a qualidade dos documentos gerados. Para avaliarmos a qualidade do sistema, devemos executar testes dinâmicos, de modo a submeter o software a determinadas condições de uso e analisar se o comportamento está de acordo com o esperado. O objetivo de identificar erros será mais efetivo se empregarmos algumas técnicas para auxiliar na identificação dos cenários de teste. Fazendo uma Reflexão 3 Definindo Casos de Testes Toda ênfase dos teses de validação está nos métodos que visam identificar os cenários possíveis de testes (casos de testes). Cada um deles representa uma situação diferenciada e única de comportamento do software, objetivando encontrar um erro. Como possuímos duas abordagens clássicas (requisitos ou estrutura interna), cada caso de teste sempre estará associado a uma delas. No entanto, os métodos a serem utilizados mudam conforme a abordagem utilizada. Cabe ao profissional de teste produzir um número suficiente de casos de teste para cada abordagem existente. 4 Início do Processamento A C F D E Término do Processamento B I J L G H Abordagem Caixa-Branca A B F E A B C D E A B I J L A G I J L H Caso de Teste 1 Caso de Teste 2 Caso de Teste 3 Caso de Teste 4 Definindo Casos de Testes 5 Definindo Casos de Testes Requisito A Caso de Teste A.1 Caso de Teste A.2 Caso de Teste A.3 Caso de Teste A.4 Requisito B Caso de Teste B.1 Caso de Teste B.2 Caso de Teste B.3 Caso de Teste B.4 Abordagem Caixa-Preta 6 Um dos maiores desafios de um processo de garantia de qualidade é conseguir medir o grau de qualidade alcançado nos testes. É através dos casos de testes que poderemos monitorar os avanços da qualidade de um software. O processo de validação do software somente terá resultados efetivos se os profissionais de testes conhecerem as principais técnicas de obtenção de casos de testes. Devemos ter sempre em mente que a qualidade de um sistema é determinada pelo que conseguimos “garantir” e isso será possível se conseguirmos simular o maior número possível de cenários de execução. Definindo Casos de Testes 7 Obter um software com qualidade pressupões a existência de um processo de desenvolvimento que assegure o comportamento do software comparando-o com os requisitos estabelecidos ni início do projeto. Devemos sempre entender que o principal objetivo de um processo de validação é a identificação de um conjunto de situações que serão empregadas em forma de testes, com o objetivo de identificar erros. Uma maior variedade de cenários permitirá um maior conjunto de simulações que serão avaliadas e comparadas com os requisitos “contratados”, o que torna importante a utilização de métodos que permitam identificar o maior número de casos de testes. Abordagem Caixa Preta 8 Os requisitos direcionam todo o processo de desenvolvimento. Cada requisito carrega consigo um conjunto de cenários possíveis dentro de uma realidade que o sistema irá atendê-lo. A decomposição de um requisito em cenários é fundamental para explorarmos todas as possibilidades envolvidas na dinâmica do software. É imprescindível explorarmos todos os cenários possíveis para cada requisito existente. Podemos decompor cada requisito em três cenários distintos: Primário; Alternativos; Exceção. Método de Decomposição de requisitos 9 Cenário Primário Situação mais básica de compreensão do requisito. Aqui devemos idealizar um cenário ótimo, no qual não existam problemas ou exceções. Cenários Alternativos São as variações possíveis dentro do cenário primário, isto é, os caminhos alternativos ou situações equivalentes que conduzirão ao mesmo objetivo. Pagar com cartão, cheque ou vale-transporte é uma variação da forma de pagamento. Pagar à vista ou parcelado é uma variação das condições de pagamento. Cenário de Exceção Trata-se dos possíveis problemas que impedem a finalização do requisito. São todas as condições impeditivas que podem ocorrer ao requisito. Um cliente não cadastrado, um cartão inválido ou problemas com cheques devolvidos são impeditivos para uma venda. Método de Decomposição de requisitos 10 Método de Decomposição de requisitos Sistema de Vendas Realizar Pagamentos Cenários Alternativos Cliente realiza pagamento com cheque. Cliente realiza pagamento com cartão de crédito. Cliente realiza pagamento parcelado. Cliente realiza pagamento da última parcela. Cliente realiza pagamento adiantado. Cliente realiza pagamento em atraso. Cenário Primário Cliente realiza pagamento em dinheiro. Cenários de Exceção Cliente realiza pagamento com cartão inválido. Cliente realiza pagamento com cheque bloqueado. Cliente realiza pagamento com cheque e histórico de mal pagador. 11 É a utilização de documentos para detalhar comportamentos e regras de negócios. Qualquer documento pode conter elementos fundamentais para auxiliar na localização de novos casos de teste e no refinamento e ampliação do esforço de planejamento de teste. No caso do projeto empregar a UML como padrão de documentação, as principais fontes para obter os casos de teste são os diagramas de atividades e os diagramas de estados. Método de Análise de Documentos 12 Os diagramas de atividades pode representar todo o fluxo de processamento de um determinado evento de negócio, revelando todos os caminhos alternativos (caminhos positivos) e as situações que impossibilitam a finalização desse evento (cenários negativos). Um bom diagrama de atividades deverá revelar o conjunto completo de casos de teste que deverão ser inseridos no planejamento. Método de Análise de Documentos 13 Método de Análise de Documentos Diagrama de Casos de Uso Cenários Positivos E A F E A Cenários Negativos B A C A D A Casos de Testes Identificados B C D E A F Diagrama de Atividades Diagramas de atividades como fonte de identificação dos casos de testes 14 No diagrama de estado, cada transição de um estado para outro deverá ser testada (cenários positivos, enquanto que as transições “proibidas” deverão ser inseridas como cenários negativos, uma vez que também deverão ser testadas. Método de Análise de Documentos 15 Abordagens Fundamentais dos Testes Cenários Positivos Casos de Testes Identificados Disponível Emprestado Restauração Refugado Análise Catalogação Doação Classificação Empréstimo Devolução Refugo Restaurar Disponibiliza Recuperação Destruição Diagrama de Estados Compra 1 2 3 6 5 4 1 2 2 3 3 4 4 2 4 5 5 6 6 1 1 Cenários Negativos 2 1 3 2 4 3 5 4 6 6 4 5 5 2 Diagramas de estados como fonte de identificação dos casos de testes Ciclo de vida de um livro 16 Aqui nós planejaremos os testes de forma a melhor exercitar as estruturas internas do software em busca do maior número de erros. Os cenários de testes devem ser modelados para que atendam ao maior número de situações, exigindo o menor esforço possível para executá-los. Abordagem Caixa Branca 17 Aqui, os testes são medidos pelo número de linhas que são acionadas sempre que determinado conjunto de casosde testes é executado. Desta forma, se determinado código possui 100 linhas e durante a execução conseguimos executar 87, nossos testes obtiveram 87% de cobertura do código. Seu grande objetivo é conseguir alcançar 100% do código, o que quer dizer que todas as linhas foram executadas ao menos uma vez. Inicialmente parece simples, porque com poucos casos de testes nós conseguimos alcançar um percentual alto de cobertura. À medida que inserimos mais casos de teste, percebemos que a progressão dos trabalhos caminha em um ritmo lento pois a maioria dos casos de testes que serão incluídos possui um mesmo fluxo principal, diferenciando em pequenos trechos de código Método de Cobertura de Linhas de Código 18 Método de Cobertura de Linhas de Código 2 3 5 7 6 8 4 9 11 1 10 O grafo de McCabe é muito útil para nos ajudar nesta tarefa. 19 O foco está na análise de todos os fluxos alternativos de processamento. O objetivo é identificar um conjunto de casos de testes que possibilitem exercitar todos os caminhos possíveis de execução e localizar falhas de iniciação de variáveis ou mesmo fluxos não previstos de processamento, que podem conduzir a erros de execução. Por ser muito complexo estabelecer uma cobertura integral de todos os caminhos possíveis, esse método é direcionado apenas para trechos de código que representem alta criticidade ou que necessitem de precisão nas financeiras, operações de segurança de acesso e afins. Método de Cobertura de Caminhos 20 Método de Cobertura de Linhas de Código 2 3 5 7 6 8 4 9 11 1 10 Repare que as estruturas de repetição dificultam muito esta tarefa. 21 O objetivo é detectar erros nas condições lógicas usadas. Os casos teste são construídos de forma a permitir a variação de valores que determinam a execução de diversos fluxos alternativos existentes. Podemos aplicar três níveis de refinamentos: Cobertura de Decisões; Cobertura de Condições; Cobertura de múltiplas Condições Método de Cobertura de Desvios Condicionais 22 Cobertura de Decisões Os casos de teste devem ser suficientes para que cada condição (simples ou composta) assuma valores verdadeiro ou falso pelo mesno uma vez. Se condição Então <escopo> Senão <escopo> Fim-se Método de Cobertura de Desvios Condicionais 1 3 2 4 23 Cobertura de Condições Os casos de testes devem ser suficientes para que cada condição simples (dentro de uma condição composta) assuma valores verdadeiro ou falso pelo menos uma vez. 1 2 Se <condição A> E <condição B) Então <escopo> 3 Senão <escopo> 4 Fim-se 5 Método de Cobertura de Desvios Condicionais 1 2 4 3 5 4 V V F F 24 Cobertura de Múltiplas Condições Emprega o mesmo critério do tópico anterior, diferenciando-se apenas pelo fato de que os casos de testes devem contemplar todas as múltiplas combinações possíveis. 1 2 Se <condição A> E <condição B) Então <escopo> 3 Senão <escopo> 4 Fim-se 5 Repare que o grafo de McCabe não contempla F e F Método de Cobertura de Desvios Condicionais 1 2 4 3 5 4 V V F F 25 Os erros mais comumente encontrados em laços são: Os referentes à falta de inicialização de variáveis (ocorre quando o laço não é executado). Quando as variáveis sofrem iniciações contínuas (ocorre quando um trecho do código está inserido incorretamente no laço). Quando um laço atinge seu limite de execução (ocorre quando determinada variável possui uma dimensão limite. Estes testes concentram-se na lógica dos laços de repetição inseridos no código. Trata-se de um conjunto de instruções que devem ser executadas até que satisfação de determinada condição. Apresentam-se em quatro configurações distintas: Método de Cobertura de Laços 26 Laços Simples Para testar um laço simples que não possua restrição referente à sua frequência de execução, os casos de teste abaixo atenderiam a todas as condições de execução a serem analisadas. Neste tipo de laço simples não existe um limitador de execução, podendo ser infinitamente processado: Não executar o laço Executar uma iteração do laço. Executar uma iteração do laço. Método de Cobertura de Laços 27 Laços Simples Para testes de laço simples cujo número máximo de iterações possíveis é “n” (limites de execução determinados por arrays), os casos de testes são mais numerosos, pois também contemplam testes com o controle de limitação do laço. Não executar o laço. Executar uma iteração do laço. Executar uma iteração do laço. Executar n iterações do laço. Executar n+1 iterações do laço Método de Cobertura de Laços 28 Laços Aninhados São estruturas de laços montadas uma dentro da outra, criando uma verdadeira árvore lógica de execução. A abordagem utilizada nos testes de laços simples não é recomendável, pois o número de casos d testes pode ser proibitivo. Para reduzir o volume de casos de testes, devemos adotar os seguintes procedimentos: Deve-se iniciar o teste a partir do laço mais interno, aplicando-se a técnica de laço simples. Nesse ponto, os outros laços devem realizar apenas uma iteração. Partindo-se do laço mais interno para o mais externo, devemos testar cada um deles com a mesma abordagem do laço simples, sendo que os laços internos já foram testados e poderiam assumir qualquer número de iterações. Método de Cobertura de Laços 29 Laços Concatenados São estruturas de laços sequenciados pela lógica definida na estrutura do código. Se esses laços concatenados forem independentes entre si, recomenda-se a técnica de laços simples. Entretanto, se esses laços são dependentes, ou seja, o contador do primeiro é usado como valor inicial do próximo, recomenda-se a utilização da técnica dos laços aninhados. Método de Cobertura de Laços 30 Laços Não estruturados Revela um má prática de programação e deve ser evitada. Os códigos que usam esse tipo de programação são difíceis de entender e manter, propiciando a introdução de erros nas eventuais manutenção do código Método de Cobertura de Laços 31 São técnicas que possibilitam aumentara extensão de cobertura e ampliar os cenários que representam os casos de testes alternativos e de exceção. Quando estamos planejando os testes, devemos identificar o menor conjunto de cenários que cubra o maior número de situações possíveis. É fundamental identificar os casos de testes que tenham a maior probabilidade de revelar erros e eliminar os caos redundantes de forma a aumentar a eficiência do processo de identificação de erros, com o menor esforço possível. Método de Refinamento dos Casos de Testes 32 É um método que divide o domínio de entrada de dados em classes (grupo de valores). Cada classe representa um possível erro a ser identificado, permitindo que os casos de testes redundantes de cada classe identificada sejam eliminados sem que a cobertura dos cenários existentes seja prejudicada. Um caso de teste ideal descobre sozinho uma classe de erros que, de outro modo, poderia exigir que muitos casos fossem executados antes que o erro geral fosse observado. Cada entrada deve ser analisada objetivando identificar um conjunto de valores válidos e inválidos. Refinamento por Partição de Equivalência 33 As classes de equivalência podem ser definidas, conforme as seguintes diretrizes: 1. Se uma condiçãode entrada especificar um intervalo, uma classe de equivalência válida e duas classes de equivalência inválidas são definidas. 2. Se uma condição de entrada exigir um valor específico, uma classe de equivalência válida e duas inválidas são definidas. 3. Se uma condição de entrada especificar um membro de um conjunto, uma classe de equivalência válida e uma inválida são definidas. 4. Se uma condição de entrada for booleana, uma classe de equivalência válida e uma inválida são definidas. Refinamento por Partição de Equivalência 34 Exemplo de refinamento por partição de equivalência: Refinamento por Partição de Equivalência Entrada Valores Permitidos Classes Casos de Teste Idade (esse valor é obtido através da digitação da data de aniversário) Número entre 18 e 120 18 a 120 Idade = 20 < 18 Idade = 10 > 120 Idade = 150 35 É um método complementar à partição de equivalência. Na abordagem anterior, qualquer valor dentro de uma classe identificada seria candidato ao caso de teste selecionado. Em tese, o software está mais susceptível ao erro nas fronteiras do domínio de dados do que propriamente nas regiões centrais, portanto, utilizar casos testes que percorram as fronteiras dos domínios aumenta mais a probabilidade de identificação de erros. Outra diferença, é que no método de partição por equivalência, o foco estava nas condições de entrada, enquanto que as condições de saída não eram exploradas. Aqui, tanto os valores de entrada quantos de saída serão analisados. Refinamento por Valores-limite 36 Refinamento por Valores-limite Geralmente, o teste de caixa branca não testa os casos que não sejam explicitamente visíveis ou enfatizados. Por exemplo, vamos imaginar dois sensores que controlam as comportas de uma usina hidrelétrica e a seguinte instrução: If (x > y) Then <escopo 1> Else <escopo 2> Endif O caso x = y nunca está sendo explicitamente testado. É possível que haja um modo em que a igualdade é percebida e venha a modificar a parte da condição da declaração original, se o entendimento do programa não atender aos requisitos ou ocorrer a existência de algumas questões de implementação. 37 Refinamento por Valores-limite A análise do valor limite leva a novos casos de teste referentes a valores adjacentes aos limites. A seleção de tais casos adicionais, aumentam a probabilidade de se detectar uma falha. Qualquer número (neste intervalo) 38 Refinamento por Probabilidade de erro É baseado na intuição e experiência p0ara testar condições que normalmente provocam erros. Produz bons resultados, pois concentram alta probabilidade de identificação de erros no software. Um histórico de origens de erros bem montado poderá destacar quais situações são as mais recorrentes e ampliar o conjunto de itens mais problemáticos. Seguem alguns exemplos de erros tradicionais. 39 Refinamento por Probabilidade de erro Tabelas vazias ou nulas – ocorre quando existem processamento que lidam com tabelas sem informação, produzindo listas vazias que não estavam previstas pelo programador. Nenhuma ocorrência – ocorre quando executamos alguma operação porém não existem informações a serem processadas. Ex.: tela na qual seria apresentada uma lista com pedidos pendentes de processamento e o programador não previu isto. Primeira execução – erros que somente se manifestam na primeira vez que executamos uma determinada operação. Ex.: abertura de conta corrente, na qual existe uma iniciação do saldo dessa conta. Quando formos executar a primeira operação para movimentar a conta, a operação de soma falha porque este não foi iniciado com ZERO, mas sim com NULO (saldo= saldo + valor-deposito). 40 Refinamento por Probabilidade de erro Valores brancos ou nulos – ocorre na entrada de dados ou durante a leitura de registros de uma tabela. Muitas vezes, os programadores não preveem que determinadas informações “obrigatórias” não estão sendo corretamente preenchidas e isto gera um erro. Valores inválidos ou negativos – ocorre frequentemente após a entrada de dados incorretos, provocados pelo processamento errado de determinadas informações inconsistentes digitadas pelo usuário. Entrada Valores Permitidos Classes Casos de Testes Idade (Este valor é obtido através da digitação da data de aniversário) Número entre 18 e 120 18 a 120 Idade = 18, Idade = 120 < 18 Idade = 17 > 120 Idade = 121 Zero Idade = Zero Negativa Data superior à data da digitação Branco Data não digitada Inválida Data inválida
Compartilhar