TDD / BDD - Definire correttamente i test, aggiustare i test, mettere i blocchi descrittivi all'interno dei blocchi

2

Vengo con TDD / BDD.

Sono un po 'confuso, però, quando si tratta di scrivere inizialmente i miei test BDD e poi aggiungere altri test dopo i test molto ampi.

Per esempio, diciamo che sto dando i primi requisiti:

  • Dovrebbe contenere un array.
  • Dovrebbe stampare un elenco.
  • Dovrebbe cercare questa condizione specifica.

Quindi scrivo i miei test:

describe('myApp', function (){
    it('should take in an array',function(){
        //expect
    });
    it('should print a list',function(){
        //expect
    });
    it('should look for this specific condition',function(){
        //expect
    });
});

Ora ho bisogno di aggiungere alcune funzionalità alla mia app per superare questi test, quindi dico che scrivo una funzione che controlla se l'app è effettivamente passata attraverso un array. Oppure controllo l'input nell'app stessa? Esempio:

myApp(anArray) {
    checkArray(anArray) // returns true or false
}

Quindi ora la mia app ha un nuovo metodo .. checkArray() . Quindi ho bisogno di rifattorizzare i miei test, ma come li modifico. Domande:

  • Scrivo un nuovo blocco describe ?
  • Posso / devo inserire un blocco describe all'interno di un blocco it ?
  • Dovrebbe essere nel mio test should be an array ?

    describe('myApp', function (){
     it('should take in an array',function(){
        describe('myApp.checkArray, {
            it('should return true given an array', function(){
                //assertORexpectORwhatever
            });
        });
    });
    

    });

O dovrei aggiungere il blocco descrittivo dopo il primo blocco descrittivo come vedo sempre, ma il mio iniziale SHOULD non sta più descrivendo myApp . Ad esempio:

describe('myApp', function (){
    describe('myApp.checkArray, {

        //Describes myApp, not the checkArray function... *my problem*
        it('should take in an array',function(){ 

            it('should return true given an array', function(){
                //assertORexpectORwhatever
            })
        })
    });
});

Sto facendo qualcosa di fondamentalmente sbagliato? Sto descrivendo il mio problema abbastanza bene?

    
posta TyMayn 27.09.2015 - 01:04
fonte

1 risposta

1

Il modo in cui componi i test tenderà a differenziarsi in base alle tue tecniche e a quelle del tuo team, ma ci sono un paio di nozioni di base che potrebbero aiutarti nella tua situazione:

Nel primo caso in cui stai chiedendo del test it('should take in an array',... : penso che il problema che stai incontrando non sia un difetto di TDD / BDD, è che questo test sarà difficile da dimostrare in modo positivo in JavaScript (il controllo del tipo con un sistema di tipo flessibile è difficile). Probabilmente sarai solo in grado di dimostrare che la tua funzione rifiuta gli elementi che non sono matrici o hanno proprietà di array, il che probabilmente è comunque abbastanza buono.

Quando si sta cercando di soddisfare un test, in genere non si dovrebbero aggiungere funzioni esclusivamente allo scopo di rispondere alla propria suite di test; anche se in alcuni casi potrebbe essere utile aggiungere una funzione come checkArray , specialmente se si intende lanciare un errore se il controllo fallisce. In entrambi i casi, i tuoi oggetti avranno bisogno di un modo per comunicare con la suite di test - quindi aggiungi qualsiasi funzionalità di cui hai bisogno per farlo; a volte questo è semplice come restituire i risultati corretti dalle tue chiamate di metodo.

Non ci sono regole hard / veloci per quello che dovrebbe essere all'interno di quel tipo di blocco - quando sto usando un framework di test con describe / it grammatica che uso descrivo i blocchi per raggruppare le funzionalità penso fa parte di un set di comportamenti correlati e potrebbe annidarli sotto qualcosa come un blocco descrittivo per my Entire App . I miei blocchi descrittivi interni potrebbero essere associati a tutte le cose in uno specifico modulo o file, potrebbe essere correlato a un particolare passaggio del ciclo di vita dell'applicazione (inizializzazione, operazione, terminazione, ecc.) O potrebbe anche essere solo un singolo oggetto / funzione all'interno del mio programma.

Non ho alcun tipo di autorità sui test o su come dovrebbero essere esattamente i tuoi file (ho detto che dipende da te e dal tuo team in precedenza, giusto?), ma ecco come appare una delle mie suite di test per i gelsomini e funziona per me:

describe("myApp.ViewModel", function() {
    beforeEach(function() {
        //setup some stuff relevent to every test
        //maybe instantiate the object to test
        //setup spies and other mock objects - spying on getJSON maybe...
    })
    describe("the constructor", function() {
        it("should return a specific type of object", function() {});
        it("should be defined but internally uninitialized", function() {});
        it("should have specific methods defined on its prototype", function() {
            // maybe I would even do sub 'it' calls here, but not really required
        });
    });
    describe("initAsync", function() {
        it("should initialize the ViewModel asynchronously", function() {});
        it("should throw an error when initialized with no endpoint", function() {});
        it("should load 3 records initialized with the 'data.svc/mock1' endpoint", function() {});
        it("should load 0 records initialized with the 'data.svc/mock2' endpoint", function() {});
        // ...
    });
    describe("submitAsync", function() {
        // ...
    });
});
describe("myApp.Utils", function() {
    // ...
});

Puoi immaginare l'intero codice impostato sopra raggruppato all'interno di un blocco describe("myApp", ...) , se questo ha reso le cose più facili da usare.

    
risposta data 01.10.2015 - 16:24
fonte

Leggi altre domande sui tag