Devo testare tutto?


28

Inizierò il mio primo vero progetto in Ruby on Rails e mi sto forzando a scrivere test TDD . Non vedo vantaggi reali nella scrittura dei test, ma poiché sembra molto importante, ci proverò.

È necessario testare ogni parte della mia applicazione, comprese le pagine statiche?


9
Questa non è davvero una domanda su rubino su rotaie. è più una domanda TDD.
Jon Strayer

4
@JonStrayer: vero? Sei sicuro che la risposta sarebbe la stessa per RoR come .NET? Vorrei suggerire che, in base alla progettazione, il RoR ha deliberatamente ridotto il costo dei test, pur non avendo la sicurezza del tipo sotto forma di un compilatore aumenta notevolmente il vantaggio dei test.
pdr

1
Per qualche ragione, questa domanda mi fa venir voglia di pubblicare una macro di immagine del Capitano Nero che urla "TEST TUTTO !!!"
Mason Wheeler

3
Non vedere il vero vantaggio nello scrivere test e scriverli per fede cieca non suona davvero bene. Continua senza scrivere test, dopo un po 'sperimenterai una regressione inattesa e capirai perché stai testando.
ZJR

1
Attendi fino a quando decidi di ristrutturare il tuo codice. Ogni volta che vengono introdotte enormi modifiche, è necessario verificare la funzionalità. Senza test dovrai passare attraverso la tua applicazione e testare manualmente tutte le funzionalità. Introduci un altro aggiornamento di grandi dimensioni e dovrai farlo di nuovo. I test unitari sono solo un modo "economico" per assicurarsi che tutto funzioni come previsto.
Evan Plaice,

Risposte:


47

TDD non riguarda i test, riguarda il design. Scrivere i test ti costringe a pensare a come dovrebbe funzionare la classe e al tipo di interfaccia di cui hai bisogno. I test sono un felice effetto collaterale che facilita il refactoring in seguito.

Quindi, tenuto conto di ciò, qual è il comportamento di una pagina statica e qual è l'interfaccia?

La mia prima risposta sarebbe "nessuna" e "nessuna".


quindi nessun test per le pagine statiche?
Matteo Pagliazzi il

TDD riguarda, in una certa misura, il design. Ma hai ancora bisogno di un'architettura. Senza un'architettura in mente, è difficile immaginare come si possa crescere organicamente da una serie di test.
Robert Harvey,

@MatteoPagliazzi A seconda del livello del test (unit test / test di integrazione / etc), forse uno o due, per confermare che le pagine statiche sono accessibili. Ma è troppo alto livello per i test unitari.
Izkata

1
@RobertHarvey Non ho detto di non provare nulla. Ho detto di non testare le pagine statiche.
Jon Strayer,

@JonStrayer: i TDD tendono a sostenere TDD come un elisir magico per il design; Mi scuso se non è quello che intendevi. :)
Robert Harvey,

32

È sempre un'analisi costi-benefici. Qual è il costo della funzionalità per te? Se il costo è elevato, prova bene e accuratamente. Se il costo è basso, prova leggermente o per niente.

C'è anche il costo del time-to-market da considerare. Forse è meglio per te offrire una funzionalità per lo più funzionante piuttosto che essere in ritardo con una funzionalità completamente funzionante.

È quasi impossibile rispondere a queste domande nell'IMO generale.

Penso che sia più importante preservare la capacità di testare nel caso in cui alcune funzionalità risultino essere più importanti di quanto si pensasse in origine.


Inoltre, suppongo che i bug in una pagina statica siano MOLTO più facili da correggere degli errori logici, degli errori di progettazione e del tipo di cose che TDD viene normalmente utilizzato per prevenire. Sia la scoperta che la correzione di errori di pagine statiche sono probabilmente abbastanza facili, e la mia impressione è che TDD sia usato per abbreviare entrambi questi processi quando richiedono più tempo di quanto si desideri. : D
Gordon Gustafson

Non lo presumo. Se hai mai avuto a che fare con comportamenti oscuri della versione del browser o strani problemi di memoria javascript probabilmente hai ottenuto un bel allenamento. Più talvolta, poiché le lingue back-end possono essere un po 'più affidabili e standard. a volte. Forse stai parlando di statico come in HTML e senza javascript.
Michael Durrant,

8

Direi di si". Se hai dei test che coprono anche le funzionalità e il codice più semplici, puoi avere la certezza che l'aggiunta di un nuovo codice non fa smettere di funzionare sul posto. Allo stesso modo, mettere un test per ogni errore che si incontra impedisce alle regressioni di insinuarsi.


"allora puoi avere la certezza che l'aggiunta di un nuovo codice non fa smettere di funzionare sul posto", in questo modo non dovrei toccare alcun pezzo di codice che ho scritto prima e aggiungere nuovi metodi?
Matteo Pagliazzi il

Beh no. Ma dipendenze impreviste e non pianificate tra il codice che attualmente "funziona" possono causare problemi se si aggiunge un nuovo codice che modifica tali dipendenze. Inoltre, se sbagli il test, che penso sia abbastanza comune, devi modificare il test stesso e quindi, forse, modificare il codice derivante da quel test.
Bruce Ediger

@Andy È un'assurdità assoluta. Testare setter e getter di proprietà è sia banale che VITAL. Se non funzionano, generalmente l'intera classe cade a pezzi. Ad esempio, in un'applicazione multithread, se il set non impedisce l'ottenimento simultaneo, si otterrà un problema di dati danneggiato che può richiedere ore per arrivare alla fine, perché l'origine dati sarà corretta, ma il risultato get non lo farà O se il tuo set non riesce ad aggiornare anche il tempo di aggiornamento, i tuoi dati possono diventare impossibili da sincronizzare Ti viene l'idea. Se setter e getter fossero davvero banali, potresti semplicemente rendere pubblica la proprietà
deworde

@deworde Temo che rendere sicuro il thread dei membri dell'istanza non sia poi così comune. È più normale controllare l'accesso al tipo non-thead safe che cercare di renderli thread-safe. Ad ogni modo, cosa testare è una questione di costi-benefici, come afferma un'altra risposta. puoi dedicare del tempo a scrivere test per getter o setter oppure puoi verificare il comportamento effettivo che il tuo sistema dovrebbe incapsulare.
Andy,

3

Sì, dovresti testare tutto ...

Non sarà necessario essere in grado di scrivere test automatizzati per tutto. Per le tue pagine statiche, cerca di utilizzare Selenium http://seleniumhq.org/ per assicurarti che le cose siano corrette.

Dalla mia esperienza, alcune cose del front-end sono quasi impossibili da scrivere per i casi di test, ma è per questo che vorresti davvero testare usando il bulbo oculare Mark 1.


Non sono d'accordo. Se non riesci a farlo accadere tramite una simulazione o il passaggio di dati, perché farlo nel tuo codice. Getter e setter non hanno bisogno che i propri test vengano testati tramite altri test unitari del sistema per verificare la funzionalità prevista.
Schleis

Certo, setter / getter sono testati indirettamente con altri test ma quando qualcuno dice "test tutto" presumo che significhino creare test in modo specifico per quel tipo di cose. Dico sempre alla gente "prova le cose importanti". Cose come setter e getter non rientrano in quella definizione per me.
Andy

2

Il test è importante quanto la codifica. Devi sentire il detto "Se qualcosa può andare storto, lo farà". INMO, Tra le molte tecniche di ingegneria del software utilizzate per migliorare la qualità, i test sono i più preziosi per aiutarti a trovare i problemi in anticipo.

Mentre testare tutto non è possibile (specialmente con piccoli team e sistemi di grandi dimensioni), ciò non significa che si salti del tutto il test. Ne vale la pena testare? Vedere la sezione "Individuazione precoce dei guasti" in Vedere Wiki-SoftwareTesting .


2

I test TDD possono anche essere specifiche viventi se scritti in questo modo. I nomi dei metodi di test dovrebbero avere senso per un utente aziendale.


2

Come altri hanno già detto, nei test su Ruby on Rails è molto più importante che nella (maggior parte) altre lingue. Ciò è dovuto alla mancanza di un compilatore.

Lingue come Delphi , C ++, VB.NET , ecc ... sono lingue compilate e il compilatore raccoglierà molti errori come errori di battitura nelle chiamate a un metodo. In Ruby on Rails saprai solo se c'è un errore di battitura o un errore nel tuo codice se quella particolare riga di codice viene eseguita o stai utilizzando un IDE che mostra avvisi visivi.

Poiché OGNI singola riga di codice è importante (altrimenti non ci sarebbe) dovresti testare ogni metodo che scrivi. Questo è molto più semplice di quanto sembri se segui alcuni strumenti TBDD di base.

Ho scoperto che Ryan Bates ' Rails Cast su How I test è stato prezioso per me e ha davvero messo in evidenza la semplicità di TBDD se fatto correttamente.


1

Se stai veramente usando la metodologia TDD, allora non scrivi il codice senza prima avere un test unitario che stai cercando di superare.


2
si ... ma ad esempio in una pagina statica cosa devo testare? l'esistenza di esso? che il contenuto e i collegamenti esistono? forse mi sbaglio ma sembra una perdita di tempo ...
Matteo Pagliazzi il

1
Tendo a pensare che la metodologia TDD sia applicata alla tua logica. La tua pagina statica è un file html? Una vista MVC che non cambia mai? Se in quest'ultimo caso immagino che potresti verificare che il tuo controller restituisca la visualizzazione corretta. Penso che la cosa più importante sia ricordare che TDD dovrebbe aiutarti a sviluppare contro le tue specifiche, non solo "testare ..."
wessiyad,

Suppongo che serviate semplicemente una pagina statica con un componente del framework. Se nessuno dei tuoi metodi tocca quella pagina, in realtà non c'è nulla da testare. Non è inoltre necessario testare Rails. Penso che qualcuno l'abbia coperto.
Erik Reppen,

0

Direi di non iniziare con TDD. Prendi una decisione informata quando hai dedicato più tempo all'apprendimento delle strategie di architettura in generale. TDD non ti lascerà saltare quei compiti, anche se potresti iniziare a crederci.

Ecco il mio problema. Quando dici che sembra un sacco di tempo sprecato in cose che non romperanno mai TDDer dirai che lo apprezzerai quando quella cosa che non avevi previsto in un'enorme catena di dipendenze viene sballata. Quando fai notare che è impossibile prevedere queste cose prima di scrivere la tua app, ed è per questo ... perché testiamo, ti dicono che è molto più sulla progettazione e non sui test anche se i test sono utili.

Ma le catene giganti di imprevedibili dipendenze collegate sono il prodotto di un design scadente?

Quindi che cos'è?

Ecco un pensiero. Non abbiamo in primo luogo enormi catene complesse di dipendenze considerando i due principi seguenti di progettazione orientata agli oggetti di Design Patterns:

"Programma per un'interfaccia, non un'implementazione"

Vale a dire, ai tuoi oggetti non dovrebbe interessare chi sta facendo la chiamata o come sono stati fatti. Solo che sono stati alimentati gli argomenti appropriati e che i metodi che chiamano da altri oggetti vengono indirizzati a funzionare come previsto. La catena di dipendenza nella maggior parte dei casi dovrebbe trovarsi in un punto di collegamento, la chiamata del metodo da parte del chiamante e il punto in cui gli arg vengono rilasciati nei metodi. È qui che accedi e convalidi e invii messaggi utili per il debug quando le cose vanno male.

E:

"Favorisci la composizione dell'oggetto rispetto all'eredità di classe"

Chi è il manichino? Il ragazzo che ha fatto qualcosa in una classe in uno schema di ereditarietà a cascata contorto che coinvolge come 30 classi con conseguente rottura del caso marginale, o lo sviluppatore che ha inventato quell'architettura in primo luogo? Il TDD potrebbe aiutarti ad arrivare al fondo dei problemi all'interno di quella torre pendente di classe Pisa prima di quanto potresti avere senza, ma ciò rende meno doloroso tentare di modificare uno degli endpoint di quel disastro del codice la prossima volta?

Ed è qui che arrivo alla cosa che mi infastidisce. TDD aiuta davvero la progettazione o abilita la cattiva architettura? Mi sembra che abbia il potenziale per essere una strategia che si autoavvera. Più il tuo team non deve assumersi la propria responsabilità per l'architettura scadente, più utili sembrano diventare quei componenti di test granulari, ma alla fine la tua app diventa un PITA sempre più grande con cui lavorare (supponendo che non abbiano mai pensato molto all'architettura nel primo posto). E l'incapacità di riconoscere le conseguenze di ciò è senza dubbio, sempre l'errore più costoso che si può fare quando si lavora su un'applicazione che dovrebbe essere aggiornata e modificata nel tempo.


-1

Per rispondere alla domanda, pensa a "cosa potrebbe andare storto qui". In particolare, se modifichi il "codice" (markup / qualunque cosa), come avrai la certezza di non aver rotto la pagina. Bene, per una pagina statica:

  • potrebbe non essere visualizzato
  • potrebbe essere visualizzato in modo errato
  • JS potrebbe non essere caricato
  • i percorsi per le immagini potrebbero non funzionare
  • i collegamenti potrebbero essere interrotti

Personalmente, consiglierei:

  • scrivi un test al selenio [1] che controlla una stringa che ti aspetti sulla pagina (se possibile vicino al fondo). Ciò convalida il rendering.
  • controlla che non ci siano errori JS (penso che il selenio lo consenta)
  • eseguire le pagine statiche attraverso un validatore html e, se possibile, un controllo link.
  • Non ho trovato uno strumento che mi piace per convalidare JS, ma potresti trovare successo con jslint o jshint.

Il take away qui è che vuoi qualcosa che sia ripetibile, facile da usare e verrà eseguito automaticamente nel tuo test runner.


-1

Solo per aggiungere a tutte le risposte già eccellenti, ecco il mio pensiero su cosa testare e cosa non testare:

Fai un test:

  • logica di business
  • logica dell'applicazione
  • funzionalità
  • comportamento,
  • quindi, tutto, davvero, tranne :

Non testare:

  • costanti
  • presentazione

Quindi non ha senso avere un test che dice:

assert wibble = 3

e del codice che dice

wibble = 3

E non ha senso anche testare le cose di presentazione, come se l'icona è in blu pervinca, quale font hai usato per le intestazioni e così via ...

Quindi, chiedi "dovrei testare le pagine statiche" e la risposta è: le testerai in quanto fanno parte della funzionalità, della logica aziendale o del comportamento del tuo sito.

Quindi, nella nostra app, abbiamo un test che verifica che i termini e le condizioni siano disponibili da ogni parte del sito - per utenti anonimi, per utenti che hanno effettuato l'accesso, dalla dashboard, all'interno delle schermate delle app ecc. Verifica solo che ci sia un link chiamato "termini e condizioni" su ogni pagina, che il link funziona, e quindi il test dice che quando arriva sulla pagina, "assomiglia" ai Ts & Cs - quel tanto che basta per rassicurarti che è la pagina giusta, senza "testare una costante" o "testare la presentazione" ... in modo da poter verificare che il testo sia corretto, ad esempio, senza controllare la dimensione del carattere o il layout del testo in particolare ...

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.