Desvantagens do desenvolvimento orientado a testes? [fechadas]


192

O que eu perco ao adotar o design orientado a testes?

Listar apenas negativos; não liste os benefícios gravados de forma negativa.


Eu adicionei uma resposta afirmando que o BDD pode aliviar alguns desses negativos. Peço que você considere esse fator ao coletar suas informações negativas, pois algumas delas podem ser eliminadas e não mais consideradas negativas.
Kilhoffer 15/09/08

25
Para esclarecimentos, não sou contra ou a favor. Estou tentando tomar uma decisão informada sobre o assunto, mas a maioria das pessoas que defendem o TDD não entende ou não admite os negativos.
31410 IanL

1
O título menciona "Desenvolvimento Orientado a Testes", mas o corpo da pergunta menciona "Design Orientado a Testes". Sobre qual dos dois é essa pergunta? Existem diferenças importantes, mas sutis, entre os dois. O design orientado a testes visa permitir que os testes conduzam o design do software. O desenvolvimento orientado a testes geralmente é associado à gravação de testes antes do código de produção (mas não necessariamente permitindo que os testes influenciem o design).
Jim Hurne

3
TDD é uma gaiola que detém a criatividade do desenvolvedor.
Lewis

13
por favor, pare de fechar questões importantes, djesus
Casper Leon Nielsen

Respostas:


129

Várias desvantagens (e não estou afirmando que não há benefícios - especialmente ao escrever a base de um projeto - economizaria muito tempo no final):

  • Grande investimento em tempo. No caso simples, você perde cerca de 20% da implementação real, mas nos casos complicados, você perde muito mais.
  • Complexidade adicional. Para casos complexos, é mais difícil calcular seus casos de teste. Em casos como esse, tente usar o código de referência automático que será executado paralelamente na versão de depuração / execução de teste, em vez do teste de unidade dos casos mais simples.
  • Impactos do projeto. Às vezes, o design não é claro no início e evolui à medida que você avança - isso forçará você a refazer seu teste, o que gerará uma grande perda de tempo. Eu sugeriria adiar testes de unidade nesse caso até que você tenha alguma idéia do design em mente.
  • Ajustes contínuos. Para estruturas de dados e algoritmos de caixa preta, os testes de unidade seriam perfeitos, mas para algoritmos que tendem a ser alterados, aprimorados ou ajustados, isso pode causar um grande investimento em tempo que se pode afirmar que não se justifica. Portanto, use-o quando achar que realmente se encaixa no sistema e não force o design a se ajustar ao TDD.

7
O ponto principal (4) é: qualquer sistema que não esteja bem definido e provavelmente mude para corresponder a um comportamento visual em evolução, diferentes especificações de IA, algoritmos comportamentais etc. causará um grande investimento em definições de teste repetidas, pois mantemos em alterar os resultados desejados do teste.
Adi

12
É verdade, mas não seria o mesmo sem o TDD? Sem ele, você teria que fazer mais testes manuais, o que sofreria o mesmo problema.
sleske

50
O "grande investimento em tempo" não poupará tempo mais tarde ao desenvolver sua solução? Especialmente com um complexo? Eu acho que você deve economizar tempo. Não pensar na fase de manutenção em que pequenas alterações podem facilmente quebrar o sistema. ( Ou talvez eu só estou sendo ingênuo sobre testes de regressão unidade + prevenindo futuros erros )
Robert Koritnik

6
Sergio / Robert, sou a favor de ter testes de unidade para sistemas genéricos e definitivamente para componentes que representam a própria base para sistemas. Dito isto, acrescentaria que é preciso diferenciar entre esses casos e a simplificação excessiva da vida real, tentando afirmar que todo sistema pode ser tratado dessa maneira. Nem todos os sistemas podem ser generalizados e simplificados para testes de unidade e, se você tentar forçar a natureza dos testes de unidade nesses sistemas, poderá acabar gastando muito mais tempo corrigindo seus testes de unidade do que realmente testando resultados reais.
Adi

3
@ Adi: Eu acho que você está errado. Na minha opinião, todo sistema pode ser testado dessa maneira, é apenas uma questão de autodisciplina.
precisa saber é o seguinte

189

Se você deseja fazer o TDD "real" (leia: teste primeiro com as etapas de vermelho, verde e refatorar), também é necessário começar a usar zombarias / stubs, quando quiser testar os pontos de integração.

Ao começar a usar zombarias, depois de um tempo, você desejará começar a usar Injeção de Dependência (DI) e um contêiner de Inversão de Controle (IoC). Para fazer isso, você precisa usar interfaces para tudo (que têm muitas armadilhas).

No final do dia, você precisa escrever muito mais código do que se você apenas fizer isso da "maneira simples e antiga". Em vez de apenas uma classe de cliente, você também precisa escrever uma interface, uma classe simulada, algumas configurações de IoC e alguns testes.

E lembre-se de que o código de teste também deve ser mantido e tratado. Os testes devem ser tão legíveis quanto todo o resto e leva tempo para escrever um bom código.

Muitos desenvolvedores não entendem como fazer tudo isso "do jeito certo". Mas como todo mundo diz a eles que o TDD é a única maneira verdadeira de desenvolver software, eles apenas tentam o melhor que podem.

É muito mais difícil do que se possa pensar. Muitas vezes, os projetos feitos com TDD acabam com muito código que ninguém realmente entende. Os testes de unidade geralmente testam a coisa errada, da maneira errada. E ninguém concorda com a aparência de um bom teste, nem mesmo os chamados gurus.

Todos esses testes tornam muito mais difícil "alterar" (ao contrário da refatoração) o comportamento do seu sistema e alterações simples tornam-se muito difíceis e demoradas.

Se você lê a literatura do TDD, sempre existem alguns exemplos muito bons, mas geralmente em aplicativos da vida real, você deve ter uma interface de usuário e um banco de dados. É aqui que o TDD fica realmente difícil, e a maioria das fontes não oferece boas respostas. E se o fazem, sempre envolve mais abstrações: objetos simulados, programação para uma interface, padrões MVC / MVP etc., que novamente exigem muito conhecimento e ... você precisa escrever ainda mais código.

Portanto, tenha cuidado ... se você não possui uma equipe entusiasta e pelo menos um desenvolvedor experiente que sabe escrever bons testes e também sabe algumas coisas sobre uma boa arquitetura, é preciso pensar duas vezes antes de seguir o caminho do TDD .


7
Usando ferramentas como Pex & Moles, você pode facilmente evitar a criação de interfaces para qualquer coisa pequena. Moles irá ajudá-lo com isso tremendamente.
Robert Koritnik 13/10/10

24
Parece uma crítica ao teste de unidade e à programação orientada a objetos, não ao TDD.
plmaheu

5
Na verdade, corrija ** teste de unidade ** - não apenas o TDD - requer zombarias / stubs. E programar em uma interface geralmente é uma boa idéia, o mesmo vale para padrões. Se você combinar interface do usuário e lógica, terá um mau momento. Se você precisar testar a interação com o banco de dados, ainda poderá zombar do seu DAO para os testes de unidade e usar a coisa real para um teste de integração.
TheMorph

1
Eu concordo que uma névoa tenha conhecimento de design e teste antes de saltar para o tdd. Isso é crítico em projetos com novos contratados, pois são novos para ambos.
Hitesh Sahu

votar na sabedoria
sabsab

66

Quando você chega ao ponto em que possui um grande número de testes, alterar o sistema pode exigir a reescrita de alguns ou de todos os seus testes, dependendo de quais foram invalidados pelas alterações. Isso pode transformar uma modificação relativamente rápida em uma que consome muito tempo.

Além disso, você pode começar a tomar decisões de design com base mais em TDD do que em bons princípios de design. Enquanto você pode ter uma solução muito simples e fácil, impossível de testar da maneira que o TDD exige, agora você tem um sistema muito mais complexo que é mais propenso a erros.


3
Definitivamente pode ser um problema, no entanto, acho que estou vendo uma diferença notável no quanto sou afetado por isso. Tudo se resume a "escrever código testável", eu acho.
Rob Cooper

2
Scott, o exemplo que eu geralmente dou é um SqlDataSource incorporado em uma página ASPX. Você não pode automatizar um teste para isso. É simples e faz o trabalho, com apenas 1 arquivo. O componente testável é o objeto SqlDataSource do MSFT, e isso já foi feito para nós. Não há necessidade de fazermos mais.
Eric Z Beard

8
+1 "você pode começar a tomar decisões de design baseadas mais em TDD do que em bons princípios de design" - a maior armadilha do TDD IMHO.
András Szepesházi

2
@ScottSaad, o problema da IMO é que o design deve ser descrito primeiro e depois validado escrevendo testes e corrigido, se necessário. Eu já vi vários casos em que as pessoas estavam comprometendo o bom design apenas para poder fazer o teste. Como resultado - a maior parte do sistema foi coberta por testes, mas o design foi realmente feio. Eu acho que isso acontece porque TDD é empurrado para as massas como metodologia muito simples, com seguinte equívoco : if part of the system is covered by tests and they pass, then everything is fine (including design).
Yuriy Nakonechnyy

3
@Yura: É interessante o que você diz que as pessoas estavam comprometendo o bom design apenas para poder fazer testes. Na minha opinião, se houvesse um bom design, não seria necessário colocá-lo em risco. Eu já vi esse projeto e a base de código foi um pesadelo, mas as pessoas pensavam o mesmo - que o design é ótimo. Concordo apenas com a parte em que o TDD é enviado às massas como uma metodologia muito simples, mas é exatamente o oposto. Na minha opinião, quando o código foi projetado corretamente, quando você faz uma pequena alteração, não há chance de frear todos os testes ou uma grande quantidade deles.
precisa saber é o seguinte

54

Eu acho que o maior problema para mim é a enorme perda de tempo que leva para "entrar nele". Ainda estou muito no início da minha jornada com o TDD (veja meu blog para atualizações, minhas aventuras de teste, se você estiver interessado) e eu literalmente passei horas começando.

Leva muito tempo para colocar seu cérebro no "modo de teste" e escrever "código testável" é uma habilidade em si.

TBH, eu discordo respeitosamente dos comentários de Jason Cohen sobre tornar públicos os métodos privados, não é disso que se trata. Não criei mais métodos públicos em minha nova maneira de trabalhar do que antes . No entanto, envolve mudanças na arquitetura e permite que você "ligue" módulos de código para tornar tudo mais fácil de testar. Você não deve tornar os internos do seu código mais acessíveis para fazer isso. Caso contrário, estamos de volta à estaca zero, com tudo sendo público, onde está o encapsulamento?

Então, (IMO) em poucas palavras:

  • A quantidade de tempo necessário para pensar (ou seja, na verdade testes de grok'ing ).
  • O novo conhecimento necessário para saber como escrever código testável.
  • Compreendendo as alterações arquiteturais necessárias para tornar o código testável.
  • Aumentando sua habilidade de "TDD-Coder" enquanto tenta melhorar todas as outras habilidades necessárias para o nosso glorioso ofício de programação :)
  • Organize sua base de código para incluir o código de teste sem estragar seu código de produção.

PS: Se você gostaria de links para positivos, eu perguntei e respondi várias perguntas sobre ele, confira meu perfil .


1
Infelizmente, a primeira resposta razoável que vi ...
Daniel C. Sobral

5
Muito prático e resposta simples - uma para o "ajuste Mind" parte
ha9u63ar

50

Nos poucos anos em que pratico o Test Driven Development, devo dizer que as maiores desvantagens são:

Venda para a gerência

TDD é melhor feito em pares. Por um lado, é difícil resistir ao desejo de apenas escrever a implementação quando você sabe como escrever uma declaração if / else . Mas um par o manterá na tarefa porque você o manterá na tarefa. Infelizmente, muitas empresas / gerentes não pensam que este seja um bom uso de recursos. Por que pagar duas pessoas para escrever um recurso, quando eu tenho dois recursos que precisam ser executados ao mesmo tempo?

Vendendo para outros desenvolvedores

Algumas pessoas simplesmente não têm paciência para escrever testes de unidade. Alguns têm muito orgulho do seu trabalho. Ou, alguns gostam de ver métodos / funções complicados sangrar no final da tela. TDD não é para todos, mas eu realmente gostaria que fosse. Isso tornaria a manutenção de coisas muito mais fácil para aquelas pobres almas que herdam código.

Mantendo o código de teste junto com o seu código de produção

Idealmente, seus testes só serão interrompidos quando você tomar uma decisão incorreta de código. Ou seja, você pensou que o sistema funcionava de uma maneira, e acontece que não. Ao quebrar um teste ou um (pequeno) conjunto de testes, essas são realmente boas notícias. Você sabe exatamente como o seu novo código afetará o sistema. No entanto, se seus testes são mal escritos, fortemente acoplados ou, pior ainda, gerados ( tosse VS Test), a manutenção de seus testes pode se tornar um coro rapidamente. E, depois que testes suficientes começarem a causar mais trabalho do que o valor percebido que eles estão criando, os testes serão a primeira coisa a ser excluída quando os agendamentos forem compactados (por exemplo, chega ao tempo de processamento)

Escrever testes para que você cubra tudo (100% de cobertura de código)

Idealmente, novamente, se você seguir a metodologia, seu código será 100% testado por padrão. Normalmente, pensei, acabo com uma cobertura de código acima de 90%. Isso geralmente acontece quando tenho alguma arquitetura de estilo de modelo e a base é testada, e tento cortar os cantos e não testar as personalizações do modelo. Além disso, descobri que, quando encontro uma nova barreira que não havia encontrado anteriormente, tenho uma curva de aprendizado em testá-la. Eu vou admitir que escrevi algumas linhas de código da maneira antiga do skool, mas eu realmente gosto de ter esses 100%. (Eu acho que eu era um realizador na escola, er skool).

No entanto, com isso, eu diria que os benefícios do TDD superam em muito os negativos da idéia simples de que, se você puder realizar um bom conjunto de testes que cubram sua aplicação, mas não sejam tão frágeis que uma alteração os interrompa, você poderá continuar adicionando novos recursos no dia 300 do seu projeto, como você fez no dia 1. Isso não acontece com todos aqueles que experimentam o TDD pensando que é uma bala mágica para todo o código deles, e assim eles acham que pode não funciona, ponto final.

Pessoalmente, descobri que, com o TDD, escrevo código mais simples, passo menos tempo debatendo se uma solução de código específica funcionará ou não, e que não tenho medo de alterar qualquer linha de código que não atenda aos critérios estabelecidos por O time.

O TDD é uma disciplina difícil de dominar, e eu pratico isso há alguns anos, e ainda aprendo novas técnicas de teste o tempo todo. É um investimento enorme de tempo, mas, a longo prazo, sua sustentabilidade será muito maior do que se você não tivesse testes de unidade automatizados. Agora, se meus chefes pudessem descobrir isso.


7
Qual foi o resto da frase que terminou com "(tosse VS Test), então principal"?
Andrew Grimm

+1 para o problema de venda. :) Estou agora em uma nova empresa e pensando em como criar uma cultura que permita que as habilidades se espalhem livremente.
Esko Luontola

2
Como você considera que algumas empresas de consultoria estão aproveitando a programação em pares e o TDD apenas para obter mais dinheiro de seus clientes. É bastante decepcionante como esses clientes pagam por idéias que parecem razoáveis ​​à primeira vista, como duas pessoas pensam muito melhor que 2 ou que o TDD garante que todas as linhas de código sejam testadas, mas no final são apenas desculpas para fazer um cliente pagar mais por algo que apenas uma pessoa pode fazer.
Lmiguelvargasf

24

No seu primeiro projeto de TDD, há duas grandes perdas, tempo e liberdade pessoal

Você perde tempo porque:

  • A criação de um conjunto abrangente, refatorado e sustentável de testes de unidade e aceitação acrescenta muito tempo à primeira iteração do projeto. Isso pode economizar tempo a longo prazo, mas também pode ser o tempo que você não precisa gastar.
  • Você precisa escolher e se tornar especialista em um conjunto principal de ferramentas. Uma ferramenta de teste de unidade precisa ser complementada por algum tipo de estrutura de simulação e ambas precisam se tornar parte do seu sistema de compilação automatizado. Você também deseja escolher e gerar métricas apropriadas.

Você perde a liberdade pessoal porque:

  • O TDD é uma maneira muito disciplinada de escrever código que tende a se espalhar contra os que estão na parte superior e inferior da escala de habilidades. Sempre escrever o código de produção de uma certa maneira e sujeitar seu trabalho a uma revisão contínua por pares pode assustar seus piores e melhores desenvolvedores e até levar à perda de funcionários.
  • A maioria dos métodos ágeis que incorporam o TDD exigem que você converse continuamente com o cliente sobre o que você pretende realizar (nesta história / dia / qualquer que seja) e quais são as vantagens e desvantagens. Mais uma vez, essa não é a xícara de chá de todos, tanto do lado dos desenvolvedores quanto dos clientes.

Espero que isto ajude


1
Não sei se é porque sou o pior ou o melhor ... mas o TDD me esfrega da maneira errada. É porque me força a entrar no modo de manutenção dupla muito cedo. Toda vez que eu mudo o design de uma classe, agora também preciso alterar os casos de teste. Espero e aceito isso de uma aula madura, mas não de uma aula que acabei de escrever na semana passada! Também posso apenas dizer que DI e TDD não são bem suportados por linguagens como Java e C #. Alguém realmente precisa criar um novo idioma para que o custo de TDD e DI seja literalmente zero . Então não teremos mais essa conversa.
John Henckel

14

O TDD exige que você planeje como suas classes funcionarão antes de escrever o código para passar nesses testes. Isso é um mais e um menos.

Acho difícil escrever testes no "vácuo" - antes que qualquer código tenha sido escrito. Na minha experiência, tenho tendência a tropeçar nos meus testes sempre que penso inevitavelmente em alguma coisa enquanto escrevia minhas aulas que esqueci enquanto escrevia meus testes iniciais. Então é hora de não apenas refatorar minhas aulas, mas também meus testes. Repita isso três ou quatro vezes e pode ser frustrante.

Prefiro escrever um rascunho de minhas aulas primeiro e depois escrever (e manter) uma bateria de testes de unidade. Depois que eu tenho um rascunho, o TDD funciona bem para mim. Por exemplo, se um bug for relatado, escreverei um teste para explorar esse bug e, em seguida, corrigirei o código para que o teste seja aprovado.


1
Embora você deva ter uma ideia de como será a arquitetura do seu sistema, não é necessário saber muito antes do TDD. Meios TDD que os testes de conduzir o projeto, por isso vai mudar como você implementar mais cenários de teste
casademora

4
Eu concordo com o vácuo. Os tutoriais originais do TDD, nos quais você escreverá o teste sem QUALQUER código - e obterá um erro de compilação - são loucos.
Mparaz 21/03/09

É uma suposição errada de que você pode escrever os testes uma vez e não alterá-los. Eles são códigos e todos os códigos requerem refatoração eventual após as alterações. Testes não é uma exceção. A refatoração de testes é essencial se você deseja mantê-los em manutenção.
Roman Konoval

12

A prototipagem pode ser muito difícil com o TDD - quando você não tem certeza de qual caminho seguirá para uma solução, escrever os testes antecipadamente pode ser difícil (além dos muito amplos). Isso pode ser uma dor.

Honestamente, eu não acho que, para o "desenvolvimento central" da grande maioria dos projetos, haja alguma desvantagem real; é muito mais falado do que deveria ser, geralmente por pessoas que acreditam que seu código é bom o suficiente para que não precisem de testes (nunca é) e pessoas que simplesmente não podem se dar ao trabalho de escrevê-las.


9

Bem, e esse alongamento, você precisa depurar seus testes. Além disso, há um certo custo de tempo para escrever os testes, embora muitas pessoas concordem que é um investimento inicial que compensa durante a vida útil do aplicativo, tanto na depuração economizada quanto na estabilidade.

O maior problema que eu pessoalmente tive com isso, porém, é adquirir a disciplina para realmente escrever os testes. Em uma equipe, especialmente uma equipe estabelecida, pode ser difícil convencê-los de que o tempo gasto vale a pena.


13
Ah - mas é aí que entra o TDTDD. Test Driven Test Driven Development.
Snowcrash 14/03

3
Eu ainda ocasionalmente encontro bugs nos meus testes de teste. Então agora eu pratico TDTDTDD.
HorseloverFat

@SnowCrash +1 Eu estava olhando o Google para saber quanto tempo as pessoas gastam testando seus testes e, em seguida, vi essa resposta. Eu o encontrei oficialmente porque estava pensando em TDTDTDD.
BalinKingOfMoria Reinstate CMs

1
Eu acredito que o futuro é (TD) <sup> ∞ </sup> TDD. Eu tenho um arquivo até agora: ele contém a letra "x".
mike roedor

Eu concordo com o @Tim. Convencer os membros a adotá-lo é a parte mais difícil.
precisa

7

Se seus testes não forem muito completos, você pode cair no falso senso de "tudo funciona" apenas porque você passa nos testes. Teoricamente, se seus testes forem aprovados, o código está funcionando; mas se pudéssemos escrever código perfeitamente na primeira vez, não precisaríamos de testes. A moral aqui é certificar-se de fazer uma verificação de sanidade por conta própria antes de chamar algo completo, não confie apenas nos testes.

Nessa nota, se a sua verificação de integridade encontrar algo que não foi testado, volte e escreva um teste.


Não acredito em nenhuma cláusula de sanidade desde que cresci.
mike roedor

7

A desvantagem do TDD é que ele geralmente está fortemente associado à metodologia 'Agile', que não dá importância à documentação de um sistema, e sim ao entendimento por que um teste 'deve' retornar um valor específico, em vez de qualquer outro, reside apenas no desenvolvedor cabeça.

Assim que o desenvolvedor deixa ou esquece o motivo pelo qual o teste retorna um valor específico e não outro, você está ferrado. O TDD é bom se estiver adequadamente documentado e cercado por documentação legível por humanos (por exemplo, gerente de cabelos pontudos) que pode ser referida em 5 anos quando o mundo muda e o aplicativo também precisa.

Quando falo em documentação, isso não é um problema de código, é uma escrita oficial que existe fora do aplicativo, como casos de uso e informações básicas que podem ser consultadas por gerentes, advogados e pelo pobre sapo que precisa atualizar seu código em 2011.


1
Perfeitamente colocado. Eu não poderia concordar mais. Para mim, os testes certamente não ajudam a descrever as definições de problemas do mundo real e de nível superior. Uma boa documentação provou seu valor uma e outra vez. Como o técnico. Nas idades da indústria, as noções testadas pelo tempo devem ser dispensadas com cautela cada vez maior. O código de auto-documentação é uma noção ridícula. Eu acredito em prototipagem, refatoração e agilidade decorrente de nunca definir um problema no início. No entanto, ironicamente, não definir excessivamente o problema no início faz do stubbing para TDD um campo minado.
wax_lyrical

1
Eu acho isso injusto. Boas práticas de TDD condenam números mágicos e testes obscuros. Os testes devem ser simples e, como preferencialmente, mais legíveis que o próprio código de produção. seus testes são a documentação. verifique se eles se parecem com isso. essa resposta parece um pouco com dizer "a documentação é ruim porque às vezes as pessoas escrevem uma documentação muito ruim" ou "as classes são ruins porque eu já vi algumas classes divinas que eram difíceis de lidar".
Sara

6

Eu encontrei várias situações em que o TDD me deixa louco. Para citar alguns:

  • Manutenção de caso de teste:

    Se você está em uma grande empresa, muitas chances são de que você não precisa escrever os casos de teste sozinho ou pelo menos a maioria deles é escrita por outra pessoa quando você entra na empresa. Os recursos de um aplicativo mudam de tempos em tempos e, se você não tiver um sistema, como o HP Quality Center, para rastreá-los, você ficará louco rapidamente.

    Isso também significa que os novos membros da equipe levarão um bom tempo para entender o que está acontecendo com os casos de teste. Por sua vez, isso pode ser traduzido em mais dinheiro necessário.

  • Complexidade de automação de teste:

    Se você automatizar alguns ou todos os casos de teste em scripts de teste executáveis ​​em máquina, precisará garantir que esses scripts de teste estejam sincronizados com os casos de teste manuais correspondentes e alinhados com as alterações do aplicativo.

    Além disso, você gastará tempo para depurar os códigos que ajudam a detectar bugs. Na minha opinião, a maioria desses erros vem da falha da equipe de teste em refletir as alterações do aplicativo no script de teste de automação. Alterações na lógica de negócios, GUI e outras coisas internas podem fazer com que seus scripts parem de ser executados ou não sejam confiáveis. Às vezes, as mudanças são muito sutis e difíceis de detectar. Uma vez que todos os meus scripts relatam falhas porque basearam seus cálculos nas informações da tabela 1, enquanto a tabela 1 agora era a tabela 2 (porque alguém trocou o nome dos objetos da tabela no código do aplicativo).


Isso não lida com o TDD. Se alguém de outro departamento estiver escrevendo seus casos de teste, você não está fazendo TDD. Se você possui casos de teste manuais, não está fazendo TDD. Se o código da sua biblioteca quebrar e seus testes falharem devido a alterações na GUI, você provavelmente também não está fazendo TDD. Isso parece mais argumentos contra grandes departamentos de QA corporativos ineficazes.
Sara

5

O maior problema são as pessoas que não sabem escrever testes de unidade adequados. Eles escrevem testes que dependem um do outro (e funcionam muito bem com o Ant, mas, de repente, falham quando eu os executo no Eclipse, apenas porque eles são executados em ordem diferente). Eles escrevem testes que não testam nada em particular - eles apenas depuram o código, verificam o resultado e o transformam em teste, chamando-o de "test1". Eles ampliam o escopo de classes e métodos, apenas porque será mais fácil escrever testes de unidade para eles. O código dos testes de unidade é terrível, com todos os problemas clássicos de programação (acoplamento pesado, métodos com 500 linhas de comprimento, valores codificados, duplicação de código) e é um inferno para manter. Por alguma estranha razão, as pessoas tratam os testes de unidade como algo inferior ao código "real" e não não se preocupam com a qualidade deles. :-(


4

Você perde muito tempo gasto escrevendo testes. Obviamente, isso pode ser salvo no final do projeto, capturando erros mais rapidamente.


Esta é realmente uma maneira negativa ou astuta de afirmar um positivo.
IanL

3

A maior desvantagem é que, se você realmente deseja fazer o TDD corretamente, terá que falhar muito antes de ter sucesso. Dado o número de empresas de software que trabalham (dólar por KLOC), você acabará sendo demitido. Mesmo que seu código seja mais rápido, mais limpo, mais fácil de manter e tenha menos erros.

Se você estiver trabalhando em uma empresa que paga pelos KLOCs (ou requisitos implementados - mesmo que não tenham sido testados), fique longe do TDD (ou revisões de código, ou programação de pares, ou Integração Contínua, etc. etc. etc.).


3

Você perde a capacidade de dizer que está "pronto" antes de testar todo o seu código.

Você perde a capacidade de escrever centenas ou milhares de linhas de código antes de executá-lo.

Você perde a oportunidade de aprender através da depuração.

Você perde a flexibilidade de enviar código do qual não tem certeza.

Você perde a liberdade de acoplar firmemente seus módulos.

Você perde a opção de ignorar a documentação de design de baixo nível.

Você perde a estabilidade que acompanha o código que todo mundo tem medo de alterar.


1
Depende da sua definição de "entregar uma solução no prazo" - é "qualquer solução antiga e parcialmente quebrada no prazo" ou "entregar soluções de trabalho no prazo". Você certamente perde a capacidade de fornecer soluções parcialmente quebradas no prazo. Quanto à velocidade do desenvolvedor, eu gosto da métrica "tempo decorrido entre o início do desenvolvedor e uma semana de implantação ao vivo sem falhas". Se você medi-lo de maneira justa, é difícil até parar o relógio em um trabalho copmlex não-TDD.
Dafydd Rees

47
-1, isso é exatamente o que o OP disse que não queria.
31710 erikkallen

1
Muitas afirmações verdadeiras, mas: o que erikkallen disse. -1.
Jrandom_hacker

@ j_random_hacker disse hacker ... LOL
Dan

apenas a terceira afirmação é legítimo "aprender através de depuração está perdido"
YEH

2

Segundo a resposta sobre o tempo de desenvolvimento inicial. Você também perde a capacidade de trabalhar confortavelmente sem a segurança dos testes. Também fui descrito como um nutbar TDD, para que você possa perder alguns amigos;)


2

É percebido como mais lento. A longo prazo, isso não é verdade em termos de tristeza, pois isso o ajudará a economizar no futuro, mas você acabará escrevendo mais código, de modo que, sem dúvida, estará gastando tempo em "testar não codificar". É um argumento imperfeito, mas você perguntou!


2

Reorientar-se para requisitos difíceis e imprevistos é o constante banimento do programador. O desenvolvimento orientado a testes obriga você a se concentrar nos requisitos mundanos já conhecidos e limita seu desenvolvimento ao que já foi imaginado.

Pense bem: é provável que você acabe projetando casos de teste específicos, para que não seja criativo e comece a pensar "seria legal se o usuário pudesse fazer X, Y e Z". Portanto, quando esse usuário começa a ficar entusiasmado com os possíveis requisitos legais X, Y e Z, seu design pode ser muito rígido em casos de teste já especificados, e será difícil ajustá-lo.

Esta, é claro, é uma faca de dois gumes. Se você gastar todo o seu tempo projetando para todos os X, Y e Z concebíveis, imagináveis ​​que um usuário possa desejar, inevitavelmente nunca concluirá nada. Se você concluir algo, será impossível que qualquer pessoa (inclusive você) tenha alguma idéia do que está fazendo no seu código / design.


Pense bem: é provável que você acabe projetando casos de teste específicos, para que não seja criativo e comece a pensar "seria legal se o usuário pudesse fazer X, Y e Z". - Na minha opinião, isso é exatamente o oposto. Ao escrever testes de unidade, você se pergunta sobre os diferentes casos de negócios, o que significa que você é criativo e possibilita prever algo imprevisto. No entanto, toda essa criatividade não é importante se a sua implementação tiver bugs.
precisa saber é o seguinte

1

Pode ser demorado e demorado escrever testes para dados "aleatórios", como feeds XML e bancos de dados (não tão difíceis). Ultimamente, passo algum tempo trabalhando com feeds de dados climáticos. É muito confuso escrever testes para isso, pelo menos porque eu não tenho muita experiência com TDD.


Esse é um problema comum. Costumo zombar deles com objetos codificados e testá-los separadamente. Sua camada de negócios deve, então, só o trabalho com dados estáticos, você dal será então testado em um ambiente controlado (onde você pode script os dados nela etc.)
Rob Cooper

1

Você perderá grandes classes com múltiplas responsabilidades. Você provavelmente também perderá métodos grandes com várias responsabilidades. Você pode perder alguma capacidade de refatorar, mas também perderá parte da necessidade de refatorar.

Jason Cohen disse algo como: TDD requer uma certa organização para o seu código. Isso pode estar errado na arquitetura; por exemplo, como os métodos privados não podem ser chamados fora de uma classe, você deve tornar os métodos não privados para torná-los testáveis.

Eu digo que isso indica uma abstração perdida - se o código privado realmente precisa ser testado, provavelmente deve estar em uma classe separada.

Dave Mann


1

Você precisa escrever aplicativos de uma maneira diferente: uma que os torne testáveis. Você ficaria surpreso com o quão difícil isso é a princípio.

Algumas pessoas acham o conceito de pensar no que vão escrever antes de escreverem muito. Conceitos como zombaria também podem ser difíceis para alguns. O TDD em aplicativos herdados pode ser muito difícil se não foram projetados para teste. TDD em torno de estruturas que não são compatíveis com TDD também pode ser uma luta.

O TDD é uma habilidade para que os desenvolvedores juniores possam ter dificuldades no início (principalmente porque não foram ensinados a trabalhar dessa maneira).

No geral, embora os contras se resolvam à medida que as pessoas se tornam hábeis e você acaba abstraindo o código 'fedorento' e tendo um sistema mais estável.


1

Leva algum tempo para entrar nele e para começar em um projeto, mas ... sempre me arrependo de não ter feito uma abordagem orientada a testes quando encontro bugs tolos que um teste automatizado poderia ter encontrado muito rápido. Além disso, o TDD melhora a qualidade do código.


1
  • teste de unidade são mais códigos para escrever, portanto, um custo inicial de desenvolvimento mais alto
  • é mais código para manter
  • aprendizado adicional necessário

1

Boas respostas a todos. Eu adicionaria algumas maneiras de evitar o lado sombrio do TDD:

  • Eu escrevi aplicativos para fazer seu próprio autoteste aleatório. O problema de escrever testes específicos é que, mesmo que você escreva muitos deles, eles cobrem apenas os casos em que você pensa. Os geradores de teste aleatório encontram problemas nos quais você não pensou.

  • Todo o conceito de muitos testes de unidade implica que você possui componentes que podem entrar em estados inválidos, como estruturas de dados complexas. Se você ficar longe de estruturas de dados complexas, há muito menos a ser testado.

  • Na medida em que seu aplicativo o permitir, seja tímido quanto ao design, que depende da ordem adequada de notificações, eventos e efeitos colaterais. Elas podem ser facilmente descartadas ou embaralhadas e, portanto, precisam de muitos testes.


Testes aleatórios pode falhar de forma intermitente, e fazer a repeti-las difícil
David Sykes

@DavidSykes: sempre que você faz um teste aleatório, registra os parâmetros, para que, se falhar, você possa repeti-lo ou repeti-lo mais tarde, mesmo que não tenha falhado. O ponto é que não depende de você pensar nos casos de teste. Se você é como eu, instintivamente gravita em direção a casos de teste seguros.
Mike Dunlavey

0

O TDD requer uma certa organização para o seu código. Isso pode ser ineficiente ou difícil de ler. Ou mesmo arquitetonicamente errado; por exemplo, como os privatemétodos não podem ser chamados fora de uma classe, você deve tornar os métodos não privados para torná-los testáveis, o que está errado.

Quando o código muda, você também precisa alterar os testes. Com a refatoração, isso pode dar muito trabalho extra.


9
Todos os métodos privados devem ser testados através dos métodos públicos que existiriam de qualquer maneira.
Garry Shutler 15/09/08

Isso não é possível com todas as classes. Às vezes você não deseja zombar de todas as dependências, etc., e apenas deseja testar um método utilitário.
Jason Cohen

+1, é verdade. Adicione a isso o requisito de, às vezes, adicionar getters / setters a campos privados, apenas para poder configurar e ler o estado corretamente para um teste de unidade, mesmo que o estado deva ser privado para a classe.
31510 erikkallen

Considere escrever seus testes como se fosse um documento de requisitos de vida. Então você veria a luz. Leia também Padrões de teste XUnit.
Scott Nimrod

0

Deixe-me acrescentar que, se você aplicar os princípios do BDD a um projeto de TDD, poderá aliviar algumas das principais desvantagens listadas aqui (confusão, mal-entendidos etc.). Se você não conhece o BDD, leia a introdução de Dan North. Ele criou o conceito em resposta a alguns dos problemas que surgiram da aplicação do TDD no local de trabalho. A introdução de Dan ao BDD pode ser encontrada aqui .

Só faço essa sugestão porque o BDD aborda alguns desses pontos negativos e atua como uma brecha. Você deve considerar isso ao coletar seus comentários.


Absolutamente. Você deve considerar o BDD ao avaliar o TDD.
User9991

Parece BDD =-driven comportamento desenvolvimento
hayalci

0

Você precisa garantir que seus testes estejam sempre atualizados, no momento em que você começa a ignorar as luzes vermelhas é o momento em que os testes se tornam sem sentido.

Você também precisa garantir que os testes sejam abrangentes ou, no momento em que um grande bug aparecer, o tipo de gerenciamento abafado que você finalmente convenceu a deixar gastar tempo escrevendo mais código irá reclamar.


0

A pessoa que ensinou o desenvolvimento ágil da minha equipe não acreditava no planejamento, você apenas escreveu o mínimo possível.

Seu lema era refatorar, refatorar, refatorar. Cheguei a entender que refatorar significava "não planejar com antecedência".


Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.