A realidade de não aprender a desenvolver software de alta qualidade
(florianbellmann.com)- Muitos projetos adiam as medidas de QA e acabam dependendo de um grande sprint de QA pouco antes do release, repetindo o mesmo caos no ciclo seguinte
- A formação em ciência da computação costuma dedicar tempo a algoritmos e linguagens, e até à gestão de projetos, mas muitas vezes não trata a garantia de qualidade de software em nível prático
- Nas empresas, quando surgem falta de orçamento, atrasos no desenvolvimento ou aumento de escopo, o QA é o primeiro a ser reduzido, e acaba sendo entregue um software frágil que passou apenas por testes mínimos e não estruturados
- Para defender QA, é melhor falar do custo de não fazer isso em termos de aumento no custo de desenvolvimento ou de mais tempo de estabilização antes do release, em vez de usar expressões abstratas como “mais estável”
- Em vez de montar todo o sistema de qualidade de uma vez, é mais realista proteger primeiro as funcionalidades centrais ligadas diretamente ao valor para o cliente e escrever testes junto com a implementação de novas funções
QA empurrado para pouco antes do release
- Em muitos projetos, o desenvolvimento avança sem medidas importantes de garantia de qualidade
- Mesmo quando a necessidade é conhecida, a execução real muitas vezes fica concentrada em um grande sprint de QA perto do release
- Essa abordagem aumenta o estresse e só consegue fazer o software funcionar no limite do aceitável
- O mesmo caos se repete no próximo ciclo de release, dificultando qualquer melhoria estrutural
A lacuna de qualidade entre formação e prática
- Os cursos de ciência da computação se concentram principalmente em algoritmos, no funcionamento do computador e na história e nos conceitos das linguagens
- Pode até haver um semestre sobre gestão de projetos ou Scrum, mas em alguns casos o QA fica totalmente de fora
- Como mais de 90% dos formados vão trabalhar em contexto corporativo, é necessário saber entregar software sem bugs dentro do tempo definido
- Tratar QA de forma negligente na formação não condiz com as exigências do trabalho real
Por que o QA é o primeiro a ser cortado nas empresas
- Quando surgem problemas de orçamento em um projeto, os padrões e medidas de QA costumam ser os primeiros a ser excluídos
- Como o QA muitas vezes fica para o fim do projeto, se o desenvolvimento se prolonga ou o escopo aumenta, falta tempo para garantir a qualidade
- Como resultado, a equipe faz apenas testes mínimos e não estruturados e depois entrega um software com estrutura frágil
- Algumas equipes têm padrões de QA, mas normalmente eles são impostos pelos membros mais seniores ao restante do time
- Mesmo com padrões, se a equipe escreve testes só para cumprir métricas de gestão do projeto, é difícil chegar a uma garantia de qualidade suficiente
O primeiro passo para quebrar o ciclo de problemas de qualidade
- Apontar a ausência de medidas de QA exige experiência e confiança
- Crunch antes do release, sistemas em produção falhando e monitoramento ausente viram um peso para toda a equipe
- Assim como refatoração, melhorias que não ficam visíveis diretamente para a gestão são difíceis de defender, e o QA pode parecer ainda mais intimidador para quem nunca fez isso direito
- É preciso levantar o problema repetidamente e retomar a discussão para criar um primeiro passo
Explicar QA na linguagem do dinheiro
- Dizer que “o software ficará mais estável” ou “será mais fácil de manter” pode soar abstrato demais para quem não trabalha no codebase
- O desenvolvedor precisa falar sobre o custo de não fazer QA
- Exemplos de formulação:
- Se não fizermos isso agora, em 4 meses o esforço e o custo de desenvolvimento vão aumentar 15%
- Se não colocarmos testes unitários em todas as funcionalidades, a etapa de estabilização do release ficará mais longa toda vez
- À medida que novas funcionalidades forem sendo adicionadas, será necessário testar manualmente os efeitos colaterais toda vez, reduzindo o progresso a cada release
- Esse formato é uma linguagem mais fácil de transmitir para o negócio e para a gestão
- No fim, medidas de QA podem melhorar a vida tanto de desenvolvedores quanto de gestores
Começar com a dose mínima eficaz
- Se o QA for planejado como um grande investimento inicial, isso pode travar o andamento do projeto e dificultar o acordo das partes interessadas
- Um ponto de partida realista é encontrar a parte mais importante da aplicação
- Normalmente existe um caso de uso, uma funcionalidade ou um comportamento central do qual toda a aplicação depende
- É melhor testar primeiro as funcionalidades centrais que precisam necessariamente funcionar corretamente para entregar valor ao cliente
- A dose mínima eficaz (MED) significa a menor dose capaz de produzir o resultado desejado
- Em QA, a MED pode ser uma destas opções:
- plano de testes manuais
- testes automatizados no pipeline
- outras medidas que garantam o comportamento central
- Depois de garantir as funcionalidades centrais, é possível ampliar a estabilidade gradualmente
- Também é importante adicionar testes unitários a cada nova funcionalidade e validar informações fora do seu controle, como APIs externas ou entrada do usuário
- QA também deve ser melhorado de forma iterativa e gradual
Perguntas de QA a fazer em um novo projeto
- Ao iniciar ou entrar em um novo projeto, é preciso verificar se existe pelo menos alguma noção de QA
- A equipe deve pensar nas seguintes perguntas:
- O que estamos entregando?
- O que precisa funcionar obrigatoriamente?
- Como vamos garantir isso?
- Quais medidas decidimos intencionalmente não adotar, e por quê?
- Registrar isso em documento e somar um plano de testes cria uma boa base para o software evoluir
- Também é recomendável revisar a abordagem escolhida periodicamente, por exemplo a cada trimestre
Escrever testes junto com a implementação
- Mesmo sem usar TDD, recomenda-se escrever os testes enquanto o software está sendo desenvolvido
- O momento de implementar uma funcionalidade é um bom momento para escrever testes
- Escrever testes ao mesmo tempo força o código a ter uma estrutura realmente testável
- Quando os testes são adicionados depois a um software já existente, muitas vezes fica evidente que o código está excessivamente acoplado ou viola o princípio da responsabilidade única
- Os testes servem como explicação de que o comportamento desejado foi compreendido e validado, e também funcionam como uma forma de documentação do código
Efeitos positivos para o projeto e para a carreira
- Ao levantar a discussão sobre qualidade e propor soluções possíveis, você mostra às pessoas ao redor que se importa com o projeto
- Discutir qualidade pode ampliar sua esfera de influência como desenvolvedor
- A qualidade de vida de desenvolvedores e gestores também pode melhorar
- O projeto pode crescer em um ritmo saudável quando existem medidas de QA
- Nem todo mundo precisa virar embaixador de QA, mas é possível começar com um pequeno MED e mostrar formas melhores de trabalhar dentro da equipe
1 comentários
Opiniões do Hacker News
Esse tipo de conteúdo é ensinado. Só que não fica nas disciplinas centrais de ciência da computação, e sim em eletivas como engenharia de software
A CMU tem até programas de mestrado e doutorado em engenharia de software, que cobrem o que o post do blog menciona e mais. Há uma grande desconexão entre CS e SE, mas não chega ao ponto de “ninguém ensina como fazer software de qualidade”
Ironicamente, quando era estudante, engenharia de software era a disciplina de que eu menos gostava. As aulas de padrões de projeto que seguiam UML rigidamente pareciam antiquadas, e as aulas de QA em que aprendíamos TDD e ferramentas do ecossistema Java também eram tediosas. Anos depois, quando entrei em uma equipe que criava workflows e ferramentas de teste para software com altos requisitos de segurança, meus colegas ficaram surpresos porque eu já sabia o que precisava ser feito
Mesmo quando ensinam, geralmente é algo antiquado ou muito literal, como escrever aplicações web. Se houvesse uma disciplina focada em implementação, trabalho em equipe e construção de sistemas complexos, eu realmente teria querido cursá-la
Esse conteúdo não deveria ficar como eletiva ou em um programa de mestrado; é preciso haver um programa de graduação em engenharia de software, e 90% dos estudantes de CS deveriam migrar para ele
A base de código era um serviço simples que oferecia varredura de vírus/malware, e foi projetada para sempre gerar trabalho adicional, incluindo scanners e assinaturas. Era uma ideia de mais de 15 anos atrás, mas poderia ter virado uma excelente disciplina contínua; é uma pena que ele não tenha conseguido convencer o departamento
Talvez não tenha sido exatamente a disciplina que definiu minha graduação, mas chegou bem perto, e o fato de a maioria das pessoas que projetam sistemas não conhecer esse conteúdo me causa ao mesmo tempo raiva e pavor existencial
É mais fácil trabalhar com pessoas que têm diploma em CS porque há menos necessidade de convencê-las da importância de bons algoritmos ou de que não se deve implementar parsers e criptografia por conta própria
Já no lado da engenharia de software, não há uma credencial confiável que indique que a ingenuidade sobre qualidade, trabalho em equipe e colaboração com outros times tenha sido igualmente polida. Surgem pessoas treinadas pela experiência de escrever rapidamente código horrível e não verificado e sair antes de os problemas explodirem; a gerência gosta delas e despreza quem fica para limpar os destroços
Protocolos baseados em strings com delimitadores claros geralmente podem ser analisados com muita facilidade, e dependendo do caso de uso basta tratar apenas uma parte deles. Claro, testes e requisitos funcionais precisam ser considerados. Se o caso for criar uma linguagem, o conselho pode ser diferente
Iniciantes fazem por conta própria; desenvolvedores intermediários e projetos de médio porte usam geradores de parser; e as pessoas que mantêm os parsers mais sofisticados também preferem escrevê-los manualmente. O GCC também usava um parser bison antigamente, mas mudou para um parser recursivo descendente escrito à mão para obter mensagens de erro melhores, e o Clang também usa recursão descendente
A única exceção que conheço pessoalmente é o jq, e por isso é difícil produzir mensagens úteis de erro de sintaxe na implementação do jq
Escrever um parser pode ser simples o bastante para caber em um único exercício, e o código de um parser escrito à mão acaba se parecendo com uma gramática LL. Parsing é a parte mais fácil de escrever compiladores ou ferramentas de linguagem; então, se um parser escrito à mão é um padrão alto demais para a equipe, o projeto inteiro pode ser suspeito. Não estou dizendo para nunca usar geradores de parser, mas eu preferiria trabalhar em um projeto com um parser escrito à mão e bem testado a um projeto que complica o build com ferramentas adicionais ou usa ferramentas antigas como Bison e ANTLR
Ainda assim, os padrões gerais parecem ter subido em relação a 20 anos atrás. Por exemplo, controle de código-fonte, testes unitários e CI/CD não são mais controversos
A premissa de que “é preciso entregar software sem bugs no prazo” é um ponto de partida bastante ruim para começar um texto sobre software de qualidade.
Se você acredita que consegue implantar código sem bugs, está na hora de mudar de profissão.
Mesmo fazendo testes unitários, testes de integração e testes de aceitação pelo usuário, uma única alteração de código significa a possibilidade de um novo bug. Quando um desenvolvedor diz “eu nunca implanto código com bugs”, dá vontade de investigar melhor o que ele quer dizer.
Quando você passa de “escrevi a função”, “testei a função” e “testei até a função chamada pela rede”, percebe que, por melhor que seja a cobertura de casos de borda e por mais rigoroso que seja o QA, sempre resta algum comportamento indefinido 0-day em uma configuração específica, um hardware específico ou um kernel específico. O máximo que se pode dizer é que, como passou por testes, olhos humanos e revisão, há uma garantia de que quase não há bugs; no fim, só resta cruzar os dedos.
Se um bug leva uma semana para corrigir, mas só é encontrado por poucos usuários em uma situação muito rara, talvez nem valha a pena corrigi-lo.
Existem cursos de ciência da computação, e também universidades que enfatizam estágios e prática. Mas muitos departamentos de CS nas universidades vieram da matemática e são centrados em teoria.
Acho isso aceitável, assim como química não é engenharia química. A universidade não é simplesmente uma escola profissionalizante; a ideia de quase todo diploma é treinar a capacidade de pensar e demonstrar habilidade para aprender conteúdos complexos.
Uma educação universitária puramente acadêmica, sem considerar se tem utilidade no mundo real, é prejudicial à educação; mas uma formação puramente profissional, que ensina apenas o método sem compreensão, também não é útil. Ainda assim, as escolas profissionalizantes reais também não são totalmente assim: mesmo que pulem as partes difíceis, costumam oferecer uma compreensão profunda das coisas importantes.
Ainda assim, é uma boa forma de ter um vislumbre do mundo profissional de software.
Isso se aprende em boas organizações de desenvolvimento. Há 10 ou 15 anos, grosso modo, eram as FAANG; hoje, um exemplo seria a TailScale.
É possível não cair em microservices inúteis, camadas e mais camadas de Docker, camadas de serialização/desserialização JSON e um monte de testes unitários só para cobertura, enquanto se ignora QuickCheck, Hypothesis e fuzzing. Também é possível adotar conjuntos de mudanças empilhadas, rotação de on-call da equipe que escreveu o código, minimizar ligação dinâmica e erros de dependência não obrigatória, projetar de acordo com runtimes de linguagens gerenciadas e exigir como “legibilidade” a sintaxe verbal legível da linguagem. Embora isso seja repetidamente ignorado, saber como entregar software de qualidade é conhecimento público.
Pode até haver ideias sobre software de qualidade, mas este comentário é difícil de entender.
Também queria saber o que observar e se há livros ou cursos recomendáveis.
É difícil chegar a métricas válidas o bastante para sustentar uma afirmação do tipo “se não fizermos isso agora, o esforço e o custo de desenvolvimento aumentarão 15% daqui a 4 meses”.
Em uma startup, dois fundadores uma vez disseram “não escreva testes unitários”. Eu não discuti; entendi que o verdadeiro significado daquilo era que eu estava lento demais e deveria entregar o mais rápido possível. Entreguei rápido, mantive a qualidade e escrevi testes unitários também. Eles não precisavam saber; só precisavam do resultado. O ponto oculto dessas discussões é que a maioria das organizações de software não sabe entregar com rapidez e qualidade ao mesmo tempo. Não existe fórmula mágica; é preciso artesanato individual, e também é um esporte de equipe. A situação varia de lugar para lugar, então alguns processos leves podem funcionar em parte, mas o efeito é limitado. No fim, é preciso uma boa equipe com experiência, valores corretos e sabedoria para focar na entrega de valor.
A premissa de que a universidade ensina como fazer software na indústria é uma afirmação bastante ousada.
Além disso, este texto parece algo dos anos 90, quando se distribuía software em CD ou disquete. Hoje, pipelines de implantação contínua muitas vezes tornam o conceito de “release” nebuloso, e isso é considerado uma boa prática. Nesse contexto, a ideia de que um departamento de QA garante manualmente que um release não tem bugs parece bastante ultrapassada.
Também há pessoas que escrevem código embarcado em dispositivos nos quais fazer upgrade não é simples.
Se você precisa da aprovação de alguém, precisa explicar a essa pessoa por que a ideia é boa.
Dizer que “é mais estável” ou que “fica mais fácil de manter” não ressoa com quem não trabalha diretamente na codebase. Desenvolvedores precisam falar sobre o custo de não fazer QA, ou seja, na linguagem do dinheiro. Mesmo que “mas este é o jeito certo!” pareça um argumento irrefutável, a pessoa que aprova pode não se importar com essa correção. Esse princípio se aplica não só a consertar software do jeito certo, mas a quase tudo no ambiente de trabalho.
Se você precisa explicar por que qualidade é importante, eles estão no mínimo tão ignorantes quanto você, talvez até mais. Uma organização assim deve aceitar seu próprio destino. Em empresas maduras, por outro lado, você é recompensado mais rápido e melhor, e também desenvolve mais rapidamente uma noção de como o negócio deve funcionar. Claro, você precisa provar por conta própria que o tempo investido leva a melhorias reais, e isso não pode ser um impulso quixotesco de amador.
É possível ter, em linhas gerais, apenas três entre qualidade, prazo curto, baixa complexidade de comunicação e pouco dinheiro; e, nesse conjunto, o tempo está mais para variável dependente
As pessoas tentam aplicar processos e estruturas de fábrica ao software, que é ao mesmo tempo um esporte coletivo e uma área da engenharia. Assim como não se ensina nem se monta um time de basquete dividindo o ataque em procedimentos por etapa e checklists, é preciso minimizar a comunicação e fazer o time se mover como um só. Isso não é construir um processo, é formar equipes e indivíduos. Faça planos, mas, como disse Moltke, nenhum plano de operações sobrevive com certeza ao primeiro contato com o inimigo. Só que a mentalidade de negócios acredita que, se o plano não saiu como previsto, é preciso acrescentar mais processos, e isso permite que o gerente culpe indivíduos no próximo fracasso. Processos têm seu lugar para garantir que as coisas aconteçam dentro de uma estrutura legal e moral, e para reduzir condições adversas, como apostar por engano todo o dinheiro de um fundo hedge durante testes. Mas, na maioria das startups e empresas, eles são usados de uma forma que não coloca a equipe no centro
Não se costuma gritar com um arquiteto tradicional perguntando quando vai terminar. Em geral, termina quando o cliente fica satisfeito ou toma uma decisão. Muito desenvolvimento é parecido com isso
Questiono se existe alguma atividade humana que consiga ensinar com sucesso o atributo chamado qualidade
Pela minha experiência, a capacidade de produzir algo de qualidade só é adquirida com prática, prática e prática
Em contrapartida, o título apenas quer dizer que programação não é uma prática industrial. Para quem prestou atenção, isso deveria ser óbvio, mas alguns se recusam a enxergar até o fim
Basta olhar para a escrita: muita gente aprende a melhorar a qualidade. Isso acontece orientando sobre o que escrever e, mais importante, sobre como refletir a respeito da qualidade do texto que acabou de escrever e melhorá-lo
A prática sempre ajuda, mas qualidade também é algo que muita gente aprende e desenvolve
Ao aprender a voar, você aprende os padrões, mas, com o tempo, aprende a estreitar as tolerâncias. Por exemplo, se em uma curva acentuada o critério de altitude é ±100 pés, isso é o mínimo; você mira 50 pés, 20 pés e, depois, algo em que o ponteiro praticamente não se mova. O objetivo é “melhor, sempre melhor; o que posso fazer melhor?”, e, no voo, você só passa se satisfizer todos os itens, não pela média geral. Culturalmente, “satisfatório” não é o fim, é o ponto de partida
Sinto que essa atitude cria um modelo muito mais colaborativo. Na aviação, todos querem sinceramente que todos tenham sucesso e, se alguém falha, você também tem parte da responsabilidade. Havia uma cultura em que, se você cometia um erro, precisava encontrar maneiras de reduzir a possibilidade de erros futuros; nas companhias aéreas, a Garantia da Qualidade das Operações de Voo (FOQA) também tem um papel grande. Em pequenas operações remotas, isso era mais informal, mas na maioria das vezes se aproximava de uma cultura “sem culpa”; o ponto central era “como podemos melhorar?”
Qualidade, tomada de decisão e “fazer a coisa certa” eram centrais na cultura da aviação. Em uma operação respeitável, se alguém julgava que o tempo estava ruim demais para operar com segurança, isso levava ao cancelamento da operação, e ninguém decolava à força só para concluir o trabalho. O setor de tecnologia, no qual entrei depois, parece o oposto. O próprio conceito de produto mínimo viável revela o problema. Não deveria ser “mínimo viável”, e sim “produto de qualidade mínima aceitável como ponto de partida”. O mínimo não deve ser o alvo; o mínimo é apenas o ponto de partida
Se você só pratica produzir lixo, apenas ficará bom em produzir lixo. Existem, de fato, pessoas que não se importam com qualidade; nesses casos, todo o pressuposto desmorona