Requisitos em Engenharia de Software
Requisitos em Engenharia de Software
“ The hardest single part of building a software system is deciding precisely what to build. –
Frederick Brooks
Este capítulo inicia com uma apresentação sobre a importância e os diversos tipos de requisitos de
software (Seção 3.1). Em seguida, caracterizamos e apresentamos as atividades que compõem o que
chamamos de Engenharia de Requisitos (Seção 3.2). As quatro seções seguintes apresentam quatro
técnicas e documentos para especificação e validação de requisitos. Na Seção 3.3, tratamos de
histórias de usuários, as quais são os principais instrumentos de Engenharia de Requisitos quando
se usa Métodos Ágeis de Desenvenvolvimento. Em seguida, na Seção 3.4 tratamos de casos de uso,
que são documentos tradicionais e mais detalhados para especificação de requisitos. Na Seção 3.5,
vamos tratar de Produto Mínimo Viável (MVP), muito usados modernamente para prospectar e
validar requisitos. Para concluir, na Seção 3.6 tratamos de Testes A/B, também muito usados hoje em
dia para validar e definir os requisitos de produtos de software.
3.1 Introdução 🔗
Requisitos definem o que um sistema deve fazer e sob quais restrições. Requisitos relacionados
com a primeira parte dessa definição — “o que um sistema deve fazer”, ou seja, suas
funcionalidades — são chamados de Requisitos Funcionais. Já os requisitos relacionados com a
segunda parte — “sob que restrições” — são chamados de Requisitos Não-Funcionais.
Alguns autores, como Ian Sommerville (link), também classificam requisitos em requisitos de
usuário e requisitos de sistema. Requisitos de usuários são requisitos de mais alto nível, escritos
por usuários, normalmente em linguagem natural e sem entrar em detalhes técnicos. Já requisitos
de sistema são técnicos, precisos e escritos pelos próprios desenvolvedores. Normalmente, um
requisito de usuário é expandido em um conjunto de requisitos de sistema. Suponha, por exemplo,
um sistema bancário. Um requisito de usuário — especificado pelos funcionários do banco — pode
ser o seguinte: “o sistema deve permitir transferências de valores para uma conta corrente de outro
banco, por meio de TEDs”. Esse requisito dá origem a um conjunto de requisitos de sistema, os quais
vão detalhar e especificar o protocolo a ser usado para realização de tais transferências entre
bancos. Portanto, requisitos de usuário estão mais próximos do problema, enquanto que requisitos
de sistema estão mais próximos da solução.
Diversas técnicas podem ser usadas para elicitação de requisitos, incluindo entrevistas com
stakeholders, aplicação de questionários, leitura de documentos e formulários da organização que
está contratando o sistema, realização de workshops com os usuários, implementação de protótipos
e análise de cenários de uso. Existem ainda técnicas de elicitação de requisitos baseadas em estudos
etnográficos. O termo tem sua origem na Antropologia, onde designa o estudo de uma cultura em
seu ambiente natural (etnos, em grego, significa povo ou cultura). Por exemplo, para estudar uma
nova tribo indígena descoberta na Amazônia, o antropólogo pode se mudar para a aldeia e passar
meses convivendo com os índios, para entender seus hábitos, costumes, linguagem, etc. De forma
análoga, em Engenharia de Requisitos, etnografia designa a técnica de elicitação de requisitos que
recomenda que o desenvolvedor se integre ao ambiente de trabalho dos stakeholders e observe —
normalmente, por alguns dias — como ele desenvolve suas atividades. Veja que essa observação é
silenciosa, isto é, o desenvolvedor não interfere e opina sobre as tarefas e eventos que estão sendo
observados.
Após elicitados, os requisitos devem ser: (1) documentados, (2) verificados e validados e (3)
priorizados.
No caso de desenvolvimento ágil, a documentação de requisitos é feita de forma simplificada, por
meio de histórias do usuário, conforme estudamos no Capítulo 2. Por outro lado, em alguns
projetos, ainda se exige um Documento de Especificação de Requisitos, no qual todos os
requisitos do software que se pretende construir — incluindo requisitos funcionais e não-funcionais
— são documentados em linguagem natural (português, inglês, etc.). Na década de 90, chegou-se a
propor um padrão para Documentos de Especificação de Requisitos, denominado Padrão IEEE 830.
Ele foi proposto no contexto de Processos Waterfall, isto é, processos que possuem uma longa fase
inicial de levantamento de requisitos. As principais seções de um documento de requisitos no
padrão IEEE 830 são mostradas na figura da próxima página.
Após sua especificação, os requisitos devem ser verificados e validados. O objetivo é garantir que
eles estejam corretos, precisos, completos, consistentes e verificáveis, conforme discutido a seguir.
Requisitos devem estar corretos. Um contra-exemplo é a especificação de forma incorreta da
fórmula para remuneração das cadernetas de poupança em um sistema bancário.
Evidentemente, uma imprecisão na descrição dessa fórmula irá resultar em prejuízos para o
banco ou para seus clientes.
Requisitos devem ser precisos, isto é, não devem ser ambíguos. No entanto, ambiguidade
ocorre com mais frequência do que gostaríamos quando usamos linguagem natural. Por
exemplo, considere essa condição: para ser aprovado um aluno precisa obter 60 pontos no
semestre ou 60 pontos no Exame Especial e ser frequente. Veja que ela admite duas
interpretações. A primeira é a seguinte: (60 pontos no semestre ou 60 pontos no Exame
Especial) e ser frequente. Porém, pode-se interpretar também como: 60 pontos no semestre ou
(60 pontos no Exame Especial e ser frequente). Conforme você observou, tivemos que usar
parênteses para eliminar a ambiguidade na ordem das operações “e” e “ou”.
Requisitos devem ser completos. Isto é, não podemos esquecer de especificar certos
requisitos, principalmente se eles forem importantes no sistema que se pretende construir.
Requisitos devem ser verificáveis, isto é, deve ser possível testar se os requisitos estão sendo
atendidos. Um contra-exemplo é um requisito que apenas requer que o sistema seja amigável.
Como os desenvolvedores vão saber se estão atendendo a essa expectativa dos clientes?
Por fim, os requisitos devem ser priorizados. Às vezes, o termo requisitos é interpretado de forma
literal, isto é, como uma lista de funcionalidades e restrições obrigatórias em sistemas de software.
No entanto, nem sempre aquilo que é especificado pelos clientes será implementado nas releases
iniciais. Por exemplo, restrições de prazo e custos podem postergar a implementação de certos
requisitos.
Adicionalmente, os requisitos podem mudar, pois o mundo muda. Por exemplo, no sistema bancário
que usamos como exemplo, as regras de remuneração das cadernetas de poupança precisam ser
atualizadas toda vez que forem modificadas pelos órgãos federais responsáveis pela definição das
mesmas. Logo, se existe um documento de especificação de requisitos, documentando tais regras,
ele deve ser atualizado, assim como o código fonte do sistema. Chama-se de rastreabilidade
(traceability) a capacidade de dado um trecho de código identificar os requisitos implementados por
ele e vice-versa (isto é, dado um requisito, identificar os trechos de código que o implementam).
Antes de concluir, é importante mencionar que Engenharia de Requisitos é uma atividade
multidisciplinar e complexa. Por exemplo, fatores políticos podem fazer com que certos stakeholders
não colaborem com a elicitação de requisitos que ameacem seu poder e status na organização.
Outros stakeholders simplesmente podem não ter tempo para se reunir com os desenvolvedores, a
fim de explicar os requisitos do sistema. A especificação de requisitos pode ser impactada ainda por
uma barreira cognitiva entre os stakeholders e desenvolvedores. Devido a essa barreira, os
desenvolvedores podem não entender a linguagem e os termos usados pelos stakeholders. Veja que
esses últimos tendem a ser especialistas de longa data na área do sistema. Portanto, eles podem se
expressar usando uma linguagem muito específica.
Mundo Real: Para entender os desafios enfrentados em Engenharia de Requisitos, em 2016, cerca
de duas dezenas de pesquisadores coordenaram um survey com 228 empresas que desenvolvem
software, distribuídas por 10 países, incluindo o Brasil (link). Quando questionadas sobre os
principais problemas enfrentados na especificação de requisitos, as dez respostas mais comuns
foram as seguintes (incluindo o percentual de empresas que apontou cada problema):
Requisitos são a “ponte” que liga um problema do mundo real a um sistema de software que o soluciona.
A figura serve para ilustrar uma situação muito comum em Engenharia de Requisitos: sistemas cujos
requisitos mudam com frequência ou cujos usuários não sabem especificar com precisão o sistema
que querem. Na verdade, já estudamos sobre tais sistemas no Capítulo 2, quando tratamos de
Métodos Ágeis. Conforme visto, quando os requisitos mudam frequentemente e o sistema não é de
missão crítica, não vale a pena investir anos na elaboração de um Documento Detalhado de
Requisitos. Corre-se o risco de quando ele ficar pronto, os requisitos já estarem obsoletos — ou um
concorrente já ter construído um sistema equivalente e dominado o mercado. Em tais sistemas,
como vimos no Capítulo 2, pode-se adotar documentos simplificados de especificação de requisitos
— chamados de Histórias de Usuários — e incorporar um representante dos clientes, em tempo
integral, ao time de desenvolvimento, para tirar dúvidas e explicar os requisitos para os
desenvolvedores. Dada a importância de tais cenários — sistemas cujos requisitos são sujeitos a
mudanças, mas não críticos — iremos iniciar com o estudo de Histórias de Usuários na Seção 3.3.
Seleção de
Livros e Audiobooks
Conteúdo sobre
Gerenciamento de Projetos
d/
-gt
todo
me
-o-
cer
nte
aco
zer-
-fa
de
arte-
-a-
vro
.b r/li
om
os.c
isit
requ
de
lise
/ana
p s:/
htt
Por outro lado, existem também aqueles sistemas com requisitos mais estáveis. Nesses casos, pode
ser importante investir em especificações de requisitos mais detalhadas. Tais especificações podem
ser também requisitadas por certas empresas, que preferem contratar o desenvolvimento de um
sistema apenas após conhecer todos os seus requisitos. Por último, eles podem ser requisitados por
organizações de certificação, principalmente no caso de sistemas que lidam com vidas humanas,
como sistemas das áreas médica, de transporte ou militar. Na Seção 3.4, iremos estudar Casos de
Uso, que são documentos detalhados para especificação de requisitos.
Uma terceira situação é quando não sabemos nem mesmo se o “problema” que vamos resolver é de
fato um problema. Ou seja, podemos até levantar todos os requisitos desse “problema” e
implementar um sistema que o resolva. Porém, não temos certeza de que esse sistema terá sucesso
e usuários. Nesses casos, o mais prudente é dar um passo atrás e primeiro testar a relevância do
problema que se planeja resolver por meio de um sistema de software. Um possível teste envolve a
construção de um Produto Mínimo Viável (MVP). Um MVP é um sistema funcional, mas que
possui apenas o conjunto mínimo de funcionalidades necessárias para comprovar a viabilidade de
um produto ou sistema. Dada a importância contemporânea de tais cenários — sistemas para
resolver problemas em mercados desconhecidos ou incertos — estudaremos mais sobre MVPs na
Seção 3.5.
Conversas entre clientes e desenvolvedores, por meio das quais os clientes explicam e
detalham o que escreveram em cada cartão. Como dito antes, a visão de métodos ágeis sobre
Engenharia de Requisitos é pragmática: como especificações textuais e completas de requisitos
não funcionam, elas foram eliminadas e substituídas por comunicação verbal entre
desenvolvedores e clientes. Por isso, métodos ágeis — conforme estudamos no Capítulo 2 —
incluem nos times de desenvolvimento um representante dos clientes, que participa do time em
tempo integral.
Confirmação, que é basicamente um teste de alto nível — de novo especificado pelo cliente —
para verificar se a história foi implementada conforme esperado. Portanto, não se trata de um
teste automatizado, como um teste de unidades, por exemplo. Mas a descrição dos cenários,
exemplos e casos de teste que o cliente irá usar para confirmar a implementação da história.
Por isso, são também chamados de testes de aceitação de histórias. Eles devem ser escritos o
quanto antes, preferencialmente no início de uma iteração. Alguns autores recomendam
escrevê-los no verso dos cartões da história.
Portanto, especificações de requisitos por meio de histórias não consistem apenas de duas ou três
sentenças, como alguns críticos de métodos ágeis podem afirmar. A maneira correta de interpretar
uma história de usuário é a seguinte: a história que se escreve no cartão é um lembrete do
representante dos clientes para os desenvolvedores. Por meio dele, o representante dos clientes
declara que gostaria de ver um determinado requisito funcional implementado na próxima iteração
(ou sprint). Mais ainda, durante todo o sprint ele se compromete a estar disponível para refinar a
história e explicá-la para os desenvolvedores. Por fim, ele também se compromete a considerar a
história implementada desde que ela satisfaça os testes de confirmação que ele mesmo especificou.
Olhando na perspectiva dos desenvolvedores, o processo funciona assim: o representante dos
clientes está nos pedindo a história resumida nesse cartão. Logo, nossa obrigação no próximo sprint
é implementá-la. Para isso, poderemos contar com o apoio integral dele para conversar e tirar
dúvidas. Além disso, ele já definiu os testes que vai usar na reunião de revisão do sprint (ou sprint
review) para considerar a história implementada. Combinamos ainda que ele não pode mudar de
ideia e, ao final do sprint, usar um teste completamente diferente para testar nossa implementação.
Boas histórias devem possuir as seguintes características (cujas iniciais em inglês dão origem ao
acrônimo INVEST):
Histórias devem ser independentes: dadas duas histórias X e Y, deve ser possível implementá-
las em qualquer ordem. Para isso, idealmente, não devem existir dependências entre elas.
Histórias devem ser abertas para negociação. Frequentemente, costuma-se dizer que histórias
(o cartão) são convites para conversas entre clientes e desenvolvedores durante um sprint.
Logo, ambos devem estar abertos a ceder em suas opiniões durante essas conversas. Os
desenvolvedores devem estar abertos para implementar detalhes que não estão expressos ou
que não cabem nos cartões da história. E os clientes devem aceitar argumentos técnicos vindos
dos desenvolvedores, por exemplo sobre a inviabilidade de implementar algum detalhe da
história conforme inicialmente vislumbrado.
Histórias devem agregar valor para o negócio dos clientes. Histórias são propostas, escritas e
priorizadas pelos clientes e de acordo com o valor que elas agregam ao seu negócio. Por isso,
não existe a figura de uma “história técnica”, como a seguinte: “o sistema deve ser
implementado em JavaScript, usando React no front-end e [Link] no backend”.
Deve ser viável estimar o tamanho de uma história. Por exemplo, quantos dias serão
necessários para implementá-la. Normalmente, isso requer que a história seja pequena, como
veremos no próximo item, e que os desenvolvedores tenham experiência na área do sistema.
Histórias devem ser sucintas e pequenas. Na verdade, até se admite histórias complexas e
grandes, as quais são chamadas de épicos. Porém, elas ficam posicionadas no fundo do
backlog, o que significa que ainda não se tem previsão de quando elas serão implementadas.
Por outro lado, as histórias do topo do backlog e que, portanto, serão implementadas em breve,
devem ser curtas e pequenas, para facilitar o entendimento e estimativa das mesmas.
Assumindo-se que um sprint tem duração máxima de um mês, deve ser possível implementar
as histórias do topo do backlog em menos de uma semana.
Histórias devem ser testáveis, isto é, elas devem ter critérios de aceitação objetivos. Como
exemplo, podemos citar: “o cliente pode pagar com cartões de crédito”. Uma vez definidas as
bandeiras de cartões de crédito que serão aceitas, essa história é testável. Por outro lado, a
seguinte história é um contra-exemplo: “um cliente não deve esperar muito para ter sua
compra confirmada”. Essa é uma história vaga e, portanto, com um critério de aceitação
também vago.
Antes de começar a escrever histórias, recomenda-se listar os principais usuários que vão interagir
com o sistema. Assim, evita-se que as histórias fiquem enviesadas e atendam às necessidades de
apenas certos usuários. Definidos esses papéis de usuários (user roles), costuma-se escrever as
histórias no seguinte formato:
“ Como um [papel de usuário], eu gostaria de [realizar algo com o sistema]
Vamos mostrar exemplos de histórias nesse formato na próxima seção. Antes, gostaríamos de
comentar que, logo no início do desenvolvimento de um sistema, costuma-se realizar um
workshop de escrita de histórias. Esse workshop reúne em uma sala representantes dos
principais usuários do sistema, que discutem os objetivos do sistema, suas principais
funcionalidades, etc. Ao final do workshop, que dependendo do tamanho do sistema pode durar
uma semana, deve-se ter em mãos uma boa lista de histórias de usuários, que demandem alguns
sprints para serem implementadas.
Primeiro, mostramos histórias propostas por usuários típicos (veja a seguir). Qualquer usuário da
biblioteca se encaixa nesse papel e, portanto, pode realizar as operações mencionadas nessas
histórias. Observe que as histórias são resumidas e não detalham como cada operação será
implementada. Por exemplo, uma história documenta que o sistema deve permitir pesquisas por
livros. No entanto, existem diversos detalhes que a história omite, incluindo os campos de pesquisa,
os filtros que poderão ser usados, o número máximo de resultados retornados em cada pesquisa, o
leiaute das telas de pesquisa e de resultados, etc. Mas lembre-se que uma história é uma promessa:
o representante dos clientes promete ter tempo para definir e explicar tais detalhes em conversas
com os desenvolvedores, durante o sprint no qual a história será implementada. Conforme já
comentado, quando se usa histórias, essa comunicação verbal entre desenvolvedores e
representante dos clientes é a principal atividade de Engenharia de Requisitos.
É importante mencionar que, de fato, os professores foram os usuários que lembraram de requisitar
as histórias acima. Eles podem ter feito isso, por exemplo, em um workshop de escrita de histórias.
Mas isso não significa que apenas professores poderão fazer uso dessas histórias. Por exemplo, ao
detalhar as histórias em um sprint, o representante dos clientes (product owner) pode achar
interessante permitir que qualquer usuário faça doações de livros e não apenas professores. Por fim,
a última história sugerida por professores — permitir devoluções em outras bibliotecas da
universidade — pode ser considerada como um épico, isto é, uma história mais complexa. Como a
universidade possui mais de uma biblioteca, o professor gostaria de realizar um empréstimo na
Biblioteca Central e devolver o livro na biblioteca do seu departamento, por exemplo. No entanto,
essa funcionalidade requer a integração dos sistemas das duas bibliotecas e, também, pessoal
disponível para transportar o livro para sua biblioteca original.
Por fim, mostramos as histórias propostas pelos funcionários da biblioteca, durante o workshop de
escrita de histórias. Veja que, geralmente, são histórias relacionadas com a organização da biblioteca
e também para garantir o seu bom funcionamento.
Antes de concluir, vamos mostrar um teste de aceitação para a história “pesquisar por livros”. Para
confirmar a implementação dessa história, o representante dos clientes definiu que gostaria de ver
as seguintes pesquisas serem realizadas com sucesso. Elas serão demonstradas e testadas durante a
reunião de entrega de histórias — chamada de Revisão do Sprint em Scrum.
Pesquisar por livros, informando título; retorna livros cujo título contém a string de busca
Pesquisar por livros cadastrados na biblioteca desde uma data até a data atual
Aprofundamento: Testes de aceitação devem ser especificados pelo representante dos clientes.
Com isso, procura-se evitar o que se denomina de gold plating. Em Engenharia de Requisitos, a
expressão designa a situação na qual os desenvolvedores decidem, por conta própria, sofisticar a
implementação de algumas histórias — ou requisitos, de forma mais genérica —, sem que isso
tenha sido pedido pelos clientes. Em uma tradução literal, os desenvolvedores ficam cobrindo as
histórias com camadas de ouro, quando isso não irá gerar valor para os usuários do sistema.
É possível criar histórias para estudo de uma nova tecnologia? Conceitualmente, a resposta é
que não se deve criar histórias exclusivamente para aquisição de conhecimento, pois histórias
devem sempre ser escritas e priorizadas pelos clientes. E elas devem ter valor para o negócio. Logo,
não vale a pena violar esse princípio e permitir que os desenvolvedores criem uma história como
“estudar o emprego do framework X na implementação da interface Web”. Por outro lado, esse
estudo pode ser uma tarefa, necessária para implementar uma determinada história. Tarefas para
aquisição de conhecimento são chamadas de spikes.
Fluxo normal:
Vamos agora detalhar alguns pontos pendentes sobre casos de uso, usando o exemplo anterior.
Primeiro, todo caso de uso deve ter um nome, cuja primeira palavra deve ser um verbo no infinitivo.
Em seguida, ele deve informar o ator principal do caso de uso. Um caso de uso pode também incluir
um outro caso de uso. No nosso exemplo, o passo 1 do fluxo normal inclui o caso de uso “autenticar
cliente”. A sintaxe para tratar inclusões é simples: menciona-se o nome do caso de uso a ser incluído,
que deve estar sublinhado. A semântica também é clara: todos os passos do caso de uso incluído
devem ser executados antes de prosseguir. Ou seja, a semântica é a mesma de macros em
linguagens de programação.
Devido à existência de fluxos de extensão, recomenda-se evitar comandos de decisão (“se”) no fluxo
normal de casos de uso. Quando uma decisão entre dois comportamentos normais for necessária,
pense em defini-la como uma extensão. Esse é um dos motivos pelos quais os fluxos de extensão,
em casos de uso reais, frequentemente possuem mais passos do que o fluxo normal. No nosso
exemplo simples, quase já temos um empate: seis passos normais contra cinco extensões.
Algumas vezes, descrições de casos de uso incluem seções adicionais, tais como: (1) propósito do
caso de uso; (2) pré-condições, isto é, o que deve ser verdadeiro antes da execução do caso de uso;
(3) pós-condições, isto é, o que deve ser verdadeiro após a execução do caso de uso; e (4) uma lista
de casos de uso relacionados.
Para concluir, seguem algumas boas práticas para escrita de casos de uso:
As ações de um caso de uso devem ser escritas em uma linguagem simples e direta. “Escreva
casos de uso como se estivesse no início do ensino fundamental” é uma sugestão ouvida com
frequência. Sempre que possível, use o ator principal como sujeito das ações, seguido de um
verbo. Por exemplo, “o cliente insere o cartão no caixa eletrônico”. Porém, se a ação for realizada
pelo sistema, escreva algo como: “o sistema valida o cartão inserido”.
Casos de uso devem ser pequenos, com poucos passos, principalmente no fluxo normal, para
facilitar o entendimento. Alistair Cockburn, autor de um conhecido livro sobre casos de uso
(link), recomenda que eles devem ter no máximo nove passos no fluxo normal. Ele afirma
literalmente o seguinte: “eu raramente encontro um caso de uso bem escrito com mais de nove
passos no cenário principal de sucesso.” Portanto, se você estiver escrevendo um caso de uso e
ele começar a ficar extenso, tente quebrá-lo em dois casos de uso menores. Outra alternativa
consiste em agrupar alguns passos. Por exemplo, os passos “usuário informa login” e “usuário
informa senha” podem ser agrupados em “usuário informa login e senha”.
Casos de uso não são algoritmos escritos em pseudo-código. O nível de abstração é maior do
que aquele necessário em algoritmos. Lembre-se de que os usuários do sistema cujos
requisitos estão sendo documentados devem ser capazes de ler, entender e descobrir
problemas em casos de uso. Por isso, evite os comandos “se”, “repita até”, etc. Por exemplo, em
vez de um comando de repetição, você pode usar algo como: “o cliente pesquisa o catálogo até
encontrar o produto que pretende comprar”.
Casos de uso não devem tratar de aspectos tecnológicos ou de design. Além disso, eles não
precisam mencionar a interface que o ator principal usará para se comunicar com o sistema.
Por exemplo, não se deve escrever algo como: “o cliente pressiona o botão verde para
confirmar a transferência”. Lembre-se que estamos na fase de documentação de requisitos e
que decisões sobre tecnologia, design, arquitetura e interface com o usuário ainda não estão
em nosso radar. O objetivo deve ser documentar “o que” o sistema deverá fazer e não “como”
ele irá implementar os requisitos especificados.
Evite casos de uso muito simples, como aqueles com apenas operações CRUD (Cadastrar,
Recuperar, Atualizar ou Update e Deletar). Por exemplo, em um sistema acadêmico não faz
sentido ter casos de uso como Cadastrar Professor, Recuperar Professor, Atualizar Professor e
Deletar Professor. No máximo, crie um caso de uso Gerenciar Professor e explique brevemente
que ele inclui essas quatro operações. Como a semântica delas é clara, isso pode ser feito em
uma ou duas sentenças. Aproveitando, gostaríamos de mencionar que não necessariamente o
fluxo normal de um caso de uso precisa ser uma enumeração de ações. Em algumas situações,
como a que estamos mencionando, é mais prático usar um texto livre.
Padronize o vocabulário adotado nos casos de uso. Por exemplo, evite usar o nome Cliente em
um caso de uso e Usuário em outro. No livro The Pragmatic Programmer (link), David Thomas
e Andrew Hunt recomendam a criação de um glossário, isto é, um documento que lista os
termos e vocabulário usados em um projeto. Segundo os autores, “é muito difícil ser bem
sucedido em um projeto no qual os usuários e desenvolvedores referem-se às mesmas coisas
usando nomes diferentes e, pior ainda, referem-se a coisas diferentes pelo mesmo nome”.
Um exemplo simples de Diagrama de Caso de Uso para o nosso sistema bancário é mostrado na
figura da próxima página. Nele estão representados dois atores: Cliente e Gerente. Cliente participa
dos seguintes casos de uso: Sacar Dinheiro e Transferir Valores. E Gerente é o ator principal do caso
de uso Abrir Conta. O diagrama também deixa explícito que Transferir Valores inclui o caso de uso
Autenticar Cliente. Por fim, veja que os casos de uso são representados dentro de um retângulo, que
delimita as fronteiras do sistema. Os dois atores são representados fora dessa fronteira.
Qual a diferença entre casos de uso e histórias de usuários? A resposta simples é que casos de
uso são especificações de requisitos mais detalhadas e completas do que histórias. Uma resposta
mais elaborada é formulada por Mike Cohn em seu livro sobre histórias (link). Segundo ele, “casos
de uso são escritos em um formato aceito tanto por clientes como por desenvolvedores, de forma
que cada um deles possa ler e concordar com o que está escrito. Portanto, o objetivo é documentar
um acordo entre clientes e time de desenvolvimento. Histórias, por outro lado, são escritas para
facilitar o planejamento de iterações e para servir como um lembrete para conversas sobre os
detalhes das necessidades dos clientes.”
Qual a origem da técnica de casos de uso? Casos de uso foram propostos no final da década de
80, por Ivar Jacobson, um dos pais da UML e também do Processo Unificado (UP) (link).
Especificamente, casos de uso foram concebidos para ser um dos principais produtos da fase de
Elaboração do UP. Conforme dito no Capítulo 2, UP enfatiza comunicação escrita entre usuários e
desenvolvedores, usando documentos como casos de uso.
Então, para deixar claro o nosso cenário, suponha que pretendemos criar um sistema novo, mas não
temos certeza de que ele terá usuários e fará sucesso. Como comentado acima, não vale a pena
passar um ou dois anos levantando os requisitos desse sistema, para então concluir que ele será um
fracasso. Por outro lado, não faz muito sentido também realizar pesquisas de mercado, para aferir a
receptividade do sistema antes de implementá-lo. Como ele é um sistema novo, com requisitos
diferentes de quaisquer sistemas existentes, os resultados de uma pesquisa de mercado podem não
ser confiáveis.
Uma solução consiste em implementar um sistema simples, com um conjunto de requisitos
mínimos, mas que sejam suficientes para testar a viabilidade de continuar investindo no seu
desenvolvimento. Em Lean Startup, esse primeiro sistema é chamado de Produto Mínimo Viável
(MVP). Costuma-se dizer também que o objetivo de um MVP é testar uma hipótese de negócio.
Lean startup propõe um método sistemático e científico para construção e validação de MVPs. Esse
método consiste em um ciclo com três passos: construir, medir e aprender (veja próxima figura).
No primeiro passo (construir), tem-se uma ideia de produto e então implementa-se um MVP para
testá-la. No segundo passo (medir), o MVP é disponibilizado para uso por clientes reais com o
intuito de coletar dados sobre a sua viabilidade. No terceiro passo (aprender), as métricas coletadas
são analisadas e geram o que se denomina de aprendizado validado (validated learning).
Pode-se concluir que o teste foi bem sucedido e, portanto, achou-se um mercado para o
sistema (um market fit). Neste caso, é hora de investir mais recursos para implementar um
sistema com um conjunto mais robusto e completo de funcionalidades.
Por fim, pode-se concluir que o MVP falhou, após várias tentativas. Então, restam duas
alternativas: (1) perecer, isto é, desistir do empreendimento, principalmente se não existirem
mais recursos financeiros para mantê-lo vivo; ou (2) realizar um pivô, isto é, abandonar a visão
original e tentar um novo MVP, com novos requisitos e para um novo mercado, mas sem
esquecer o que se aprendeu com o MVP anterior.
Ao tomar as decisões acima, um risco é usar apenas métricas de vaidade (vanity metrics). Essas
são métricas superficiais que fazem bem para o ego dos desenvolvedores e gerentes de produto,
mas que não ajudam a entender e aprimorar uma estratégia de mercado. O exemplo clássico é o
número de pageviews em um site de comércio eletrônico. Pode fazer muito bem dizer que o site
atrai milhões de clientes por mês, mas somente isso não vai ajudar a pagar as contas do
empreendimento. Por outro lado, métricas que ajudam a tomar decisões sobre o futuro de um MVP
são chamadas de métricas acionáveis (actionable metrics). No caso de um sistema de comércio
eletrônico, essas métricas incluiriam o percentual de visitantes que fecham compras, o valor de cada
ordem de compra, o número de itens comprados, o custo de captação de novos clientes, etc. Ao
monitorar essas métricas, pode-se concluir, por exemplo, que a maioria dos clientes compra apenas
um item ao fechar uma compra. Como resultado concreto — ou acionável — pode-se decidir
incorporar um sistema de recomendação ao site ou, então, investigar o uso de um sistema de
recomendação mais eficiente. Tais sistemas, dada uma compra em andamento, são capazes de
sugerir novos itens para serem comprados. Assim, eles têm o potencial de incrementar o número de
itens comprados em uma mesma transação.
Para avaliar MVPs que incluem vendas de produtos ou serviços, costuma-se usar métricas de funil
(funnel metrics), que capturam o nível de interação dos usuários com um sistema. Um “funil” pode
incluir as seguintes métricas:
O primeiro é o caso da Zappos, uma das primeiras empresas a tentar vender sapatos pela Internet
nos Estados Unidos. Em 1999, para testar de forma pioneira a viabilidade de uma loja de sapatos
virtual, o fundador da empresa concebeu um MVP simples e original. Ele visitou algumas lojas de
sapatos de sua cidade, fotografou diversos pares de sapato e criou uma página Web bastante
simples, por meio da qual os clientes poderiam selecionar os sapatos que desejassem comprar.
Porém, todo o processamento era feito de forma manual, incluindo a comunicação com a empresa
de cartões de crédito, a compra dos sapatos nas lojas da cidade e a remessa para os clientes. Não
existia nenhum sistema para automatizar essas tarefas. No entanto, com esse MVP baseado em
tarefas manuais, o dono da Zappos conseguiu validar de forma rápida e barata a sua hipótese inicial,
isto é, de que havia mercado para venda de sapatos pela Internet. Anos mais tarde, a Zappos foi
adquirida pela Amazon, por mais de um bilhão de dólares.
Um segundo exemplo de MVP que não envolveu a disponibilização de um software real para os
usuários vem do Dropbox (o sistema de compartilhamento e armazenamento de arquivos na
nuvem). Para receber feedback sobre o produto que estavam desenvolvendo, um dos fundadores da
empresa gravou um vídeo simples, quase amador, demonstrando em 3 minutos as principais
funcionalidades e vantagens do sistema que estavam desenvolvendo. O vídeo viralizou e contribuiu
para aumentar a lista de usuários interessados em realizar um teste do sistema (de 5 mil para 75 mil
usuários). Outro fato interessante é que os arquivos usados no vídeo tinham nomes engraçados e
que faziam referência a personagens de histórias em quadrinhos. O objetivo era chamar a atenção
de adotantes iniciais (early adopters), que são aquelas pessoas aficionadas por novas tecnologias e
que se dispõem a serem as primeiras a testar e comprar novos produtos. A hipótese que se queria
validar com o MVP em forma de vídeo é que havia usuários interessados em instalar um sistema de
sincronização e backup de arquivos. Essa hipótese se revelou verdadeira pela atração de um grande
número de adotantes iniciais dispostos a fazer um teste beta do Dropbox.
No entanto, MVPs também podem ser implementados na forma de sistemas de software reais,
embora mínimos. Por exemplo, no início de 2018, nosso grupo de pesquisa na UFMG iniciou o
projeto de um sistema para catalogar a produção científica brasileira em Ciência da Computação. A
primeira decisão foi construir um MVP, cobrindo apenas artigos em cerca de 15 conferências da
área de Engenharia de Software. Nessa primeira versão, o código implementado em Python tinha
menos de 200 linhas. Os gráficos mostrados pelo sistema, por exemplo, eram planilhas do Google
Spreadsheets embutidas em páginas HTML. Esse sistema — inicialmente chamado CoreBR — foi
divulgado e promovido em uma lista de e-mails da qual participam os professores brasileiros de
Engenharia de Software. Como o sistema atraiu um bom interesse, medido por meio de métricas
como duração das sessões de uso, decidimos investir mais tempo na sua construção. Primeiro, seu
nome foi alterado para CSIndexbr (link). Depois, expandimos gradativamente a cobertura para mais
20 áreas de pesquisa em Ciência da Computação e quase duas centenas de conferências. Passamos
a cobrir também artigos publicados em mais de 170 periódicos. O número de professores com
artigos indexados aumentou de menos de 100 para mais de 900 professores. A interface do usuário
deixou de ser um conjunto de planilhas e passou a ser um conjunto de gráficos implementados em
JavaScript.
Apenas startups devem usar MVPs? Definitivamente não. Como tentamos discutir nesta seção,
MVPs são um mecanismo para lidar com incerteza. Isto é, quando não sabemos se os usuários vão
gostar e usar um determinado produto. No contexto de Engenharia de Software, esse produto é um
software. Claro que startups, por definição, são empresas que trabalham em mercados de extrema
incerteza. Porém, incerteza e riscos também podem caracterizar software desenvolvido por diversos
tipos de organização, privadas ou públicas; pequenas, médias ou grandes; e dos mais diversos
setores.
Quando não vale a pena usar MVPs? De certo modo, essa pergunta foi respondida na questão
anterior. Quando o mercado de um produto de software é estável e conhecido, não há necessidade
de validar hipóteses de negócio e, portanto, de construir MVPs. Em sistemas de missão crítica,
também não se cogita a construção de MVPs. Por exemplo, está fora de cogitação construir um MVP
para um software de monitoramento de pacientes de UTIs.
Um MVP é um produto de baixa qualidade? Essa pergunta é mais complexa de ser respondida.
Porém, é verdade que um MVP deve ter apenas a qualidade mínima necessária para avaliar um
conjunto de hipóteses de negócio. Por exemplo, o código de um MVP não precisa ser de fácil
manutenção e usar os mais modernos padrões de design e frameworks de desenvolvimento, pois
pode ser que o produto se mostre inviável e seja descartado. Na verdade, em um MVP, qualquer
nível de qualidade a mais do que o necessário para iniciar o laço construir-medir-aprender é
considerado desperdício. Por outro lado, é importante que a qualidade de um MVP não seja tão ruim
a ponto de impactar negativamente a experiência do usuário. Por exemplo, um MVP hospedado em
um servidor Web com problemas de disponibilidade pode dar origem a resultados chamados de
falsos negativos. Eles ocorrem quando a hipótese de negócio é falsamente invalidada. No nosso
exemplo, o motivo do insucesso não estaria no MVP, mas sim no fato de os usuários não
conseguirem acessar o sistema, pois o servidor frequentemente estava fora do ar.
3.5.3 Construindo o Primeiro MVP 🔗
Lean startup não define como construir o primeiro MVP de um sistema. Em alguns casos isso não é
um problema, pois os proponentes do MVP têm uma ideia precisa de suas funcionalidades e
requisitos. Então, eles já conseguem implementar o primeiro MVP e, assim, iniciar o ciclo construir-
medir-aprender. Por outro lado, em certos casos, mesmo a ideia do sistema pode não estar clara.
Nesses casos, recomenda-se construir um protótipo antes de implementar o primeiro MVP.
Design Sprint é um método proposto por Jake Knapp, John Zeratsky e Braden Kowitz para testar e
validar novos produtos por meio de protótipos, não necessariamente de software (link). As
principais características de um design sprint — não confundir com um sprint, de Scrum — são as
seguintes:
Objetivos e regras claras. Os três primeiros dias do design sprint têm como objetivo convergir,
depois divergir e, então, convergir novamente. Isto é, no primeiro dia, entende-se e delimita-se
o problema que se pretende resolver. O objetivo é garantir que, nos dias seguintes, a equipe
estará focada em resolver o mesmo problema (convergência). No segundo dia, possíveis
alternativas de solução são propostas, de forma livre (divergência). No terceiro dia, escolhe-se
uma solução vencedora, dentre as possíveis alternativas (convergência). Nessa escolha, a última
palavra cabe ao tomador de decisões, isto é, um design sprint não é um processo puramente
democrático. No quarto dia, implementa-se um protótipo, que pode ser simplesmente um
conjunto de páginas HTML estáticas, sem qualquer código ou funcionalidade. No último dia,
testa-se o protótipo com cinco clientes reais, com cada um deles usando o sistema em sessões
individuais.
Antes de concluir, é importante mencionar que design sprint não é voltado apenas para definição de
um protótipo de MVP. A técnica pode ser usada para propor uma solução para qualquer problema.
Por exemplo, pode-se organizar um design sprint para reformular a interface de um sistema, já em
produção, mas que está apresentando uma alta taxa de abandono.
Para rodar testes A/B, precisamos de uma métrica para medir os ganhos obtidos com a versão de
tratamento. Essa métrica é genericamente chamada de taxa de conversão. No nosso exemplo,
vamos assumir que ela é o percentual de visitas que se convertem em compras por meio de links
recomendados. A expectativa é que o novo algoritmo de recomendação aumente esse percentual.
Por fim, precisamos instrumentar o sistema de forma que metade dos clientes use a versão de
controle (com o algoritmo tradicional) e a outra metade use a versão de tratamento (com o novo
algoritmo de recomendação, que está sendo testado). Além disso, é importante que essa seleção
seja aleatória. Ou seja, quando um usuário entrar no sistema, iremos escolher aleatoriamente qual
versão ele irá usar. Para isso, podemos modificar a página principal, incluindo o seguinte trecho de
código:
O tamanho da amostra de um teste A/B diminui bastante quando os testes envolvem eventos com
maior taxa de conversão e que testam ganhos de maior proporção. No exemplo anterior, se a taxa
de conversão fosse de 10% e a melhoria a ser testada fosse de 25%, o tamanho da amostra cairia
para 1.800 clientes, para cada grupo. Esses valores foram estimados usando a calculadora de testes
A/B da empresa Optimizely, disponível neste link.
Se erros do Tipo I não podem ser evitados, podemos, pelo menos, ter uma ideia da probabilidade
com que eles ocorrem. Mais especificamente, em Testes A/B, existe um parâmetro de entrada,
chamado Nível de Significância (significance level) e representado pela letra grega α (alfa). Esse
parâmetro define a probabilidade de ocorrência de erros do Tipo I.
Por exemplo, suponha que α seja definido em 5%. Então, existe uma probabilidade de 5% de rejeitar
H0 indevidamente. No exemplo usado anteriormente nesta seção, em vez de α, usamos como
parâmetro de entrada o valor (1 - α), que é a probabilidade de rejeitar H0 corretamente.
Normalmente, esse valor é chamado de Nível de Confiança. Tomamos essa decisão porque (1 - α) é
o parâmetro de entrada mais comum de calculadoras de tamanho de amostras de Testes A/B.
Posso testar mais de duas variações? Sim, a metodologia que explicamos adapta-se a mais de
dois testes. Basta dividir os acessos em três grupos aleatórios, por exemplo, se quiser testar três
versões de um sistema. Esses testes, com mais de um tratamento, são chamados de Testes A/B/n.
Posso terminar o teste A/B antes, se ele apresentar o ganho esperado? Não, esse é um erro
frequente e grave. Se o tamanho da amostra for de 200 mil usuários, o teste — de cada grupo —
somente pode ser encerrado quando alcançarmos exatamente esse número de usuários. Sendo
mais preciso, ele não deve terminar antes, com menos usuários, nem depois, com mais usuários. Um
possível erro de desenvolvedores quando começam a usar testes A/B consiste em encerrar o teste
no primeiro dia em que o ganho mínimo esperado for alcançado, sem testar o resto da amostra.
O que é um teste A/A? É um teste no qual os dois grupos, controle e tratamento, executam a
mesma versão do sistema. Logo, assumindo-se uma confiança estatística de 95%, eles deveriam
quase sempre falhar, pois a versão A não pode ser melhor do que ela mesma. Testes A/A são
recomendados para testar e validar os procedimentos e decisões metodológicas que foram tomados
em um teste A/B. Alguns autores chegam a recomendar que não se deve iniciar testes A/B antes de
realizar alguns testes A/A (link). Caso os testes A/A não falhem, deve-se depurar o sistema de
experimentação até descobrir a causa raiz (root cause) que está fazendo com que uma versão A seja
considerada melhor do que ela mesmo.
Qual a origem dos termos grupos de controle e de tratamento? Os termos têm sua origem na
área médica, mais especificamente em experimentos randomizados controlados (randomized
control experiments). Por exemplo, para lançar uma nova droga no mercado, empresas
farmacêuticas devem realizar esse tipo de experimento. São escolhidas duas amostras, chamadas de
controle e de tratamento. Os participantes da amostra de controle recebem um placebo e os
participantes da amostra de tratamento são tratados com a droga. Após o teste, comparam-se os
resultados para verificar se o uso da droga foi efetivo. Experimentos randomizados controlados são
um modo cientificamente aceito de provar causalidade. No nosso exemplo, eles podem, por
exemplo, provar que a droga testada causou a cura de uma doença.
Mundo Real: Testes A/B são usados por todas as grandes empresas da Internet. A seguir,
reproduzimos depoimentos de desenvolvedores e cientistas de três empresas sobre esses testes: