Perché dovresti scrivere unit test per controller?


22

Per me questo è un test unitario del tutto irrilevante e non capisco perché qualcuno avrebbe trascorso del tempo a scriverlo, poiché c'è poco valore da guadagnare da esso. Saprei perfettamente se questo controller restituisse il tipo desiderato eseguendo il metodo in un browser. Credi davvero che sia necessario un test per questo e perché?

public class ConstituencyControllerTests
{
    private ConstituencyController _constituencyController;
    private Mock<IConstituencyService> _IConstituencyServiceMock;

    public ConstituencyControllerTests() {
        _IConstituencyServiceMock = new Mock<IConstituencyService>();
    }

    [Test]
    public async Task I_Check_For_Return_Type_And_Result() {
        _constituencyController = new ConstituencyController( _IConstituencyServiceMock.Object );

        var result = await _constituencyController.Get();
        var content = ( (dynamic)result ).Content;

        Assert.IsEmpty( content );
        Assert.IsInstanceOf( typeof( System.Web.Http.Results.OkNegotiatedContentResult<IEnumerable<ListOfConstituencies>> ), result );
        _IConstituencyServiceMock.Verify( x => x.ListOfConstituencies(), Times.Once() );
    }
}


7
Non sono d'accordo con quel @gnat. Non si tratta necessariamente di costrutti di linguaggio, ma del tipo di risultato restituito da un controller. Mentre può ridursi a una specie di stessa cosa quando non hai una gerarchia di ereditarietà, diventa una bestia completamente diversa quando il controller si aspetta che gli Antenati vengano restituiti, il controller ha restituito Person e ora Person viene cambiato per discendere non da Ancestor, ma PeopleAncestor ... Risponde anche al motivo per cui testare un metodo del genere può essere una buona idea ...;) I test unitari hanno lo scopo di raccogliere situazioni in cui un cambiamento in una cosa c / romperebbe qualcos'altro.
Marjan Venema,


Tendo ad essere d'accordo, in genere non passo molto tempo a testare i punti di ingresso dell'applicazione. È come test unitario un metodo principale di un'applicazione console. ha poco senso per me.
Mvision,

Risposte:


29

Il punto chiave è qui:

Saprei perfettamente se questo controller restituisse il tipo desiderato eseguendo il metodo in un browser

Unit-tesing riguarda l' automazione del test di non regressione semplici unità di codice, non che tu sembri. Non vuoi fare te stesso sempre unità nella tua applicazione.

EDIT: Aggiunta del commento @anotherdave:

Si tratta di facilità di ridimensionamento. Il test di un controller in un browser potrebbe essere OK; che dire di 10, 20, 50 controller? Scriverai il test una volta; potrebbe essere necessario aggiornarlo quando si cambia il controller, che è sovraccarico. Ma quanto spesso ti dispieghi? Sicuramente un controllo manuale ogni volta che c'è molto più sovraccarico del test

In alternativa a risposta @ Vladislav , test di unità assolutamente tutto può essere eccessivo e davvero indesiderabile. Se hai bisogno di qualcosa di più leggero, puoi fare test di non regressione di livello superiore usando Selenium. Sicuramente avrai meno copertura dei test unitari, ma puoi ottenere una copertura irrinunciabile che costa molto meno tempo a fare test unitari ed è più flessibile.

Cioè, se testate tutto ciò che dovete aggiornare uno o più test ogni volta che modificate un semplice elemento.


4
Anche per aggiungere re: I would know perfectly well if this controller returned the wanted type by executing the method in a browser.- si tratta di facilità di ridimensionamento. Il test di un controller in un browser potrebbe essere OK; che dire di 10, 20, 50 controller? Scriverai il test una volta; potrebbe essere necessario aggiornarlo quando si cambia il controller, che è sovraccarico. Ma quanto spesso ti dispieghi ? Sicuramente un controllo manuale ogni volta che c'è molto più sovraccarico del test.
AnotherDave,

"Unit-tesing riguarda l'automazione" - Corretto, tuttavia lo sono anche i test di integrazione (Selenium / Webdriver / ecc.). Non credo sia necessariamente così semplice che i test unitari siano più veloci da implementare rispetto ai test di integrazione. Molto dipende dall'approccio, tuttavia se ottenere un test unitario efficace richiede derisione di una dozzina di servizi diversi e chiamate effettuate in ognuno, un test di integrazione potrebbe essere più veloce da implementare e più semplice da mantenere (anche se generalmente molto più lento da eseguire, sì) . Il punto è che molto dipende dal contesto e dalla complessità del codice testato.
aroth,

@anotherdave commento aggiunto
Walfrat

@aroth il mio punto era l'opposto, il test unitario completo di un codice è qualcosa che richiede molto tempo e rende il codice molto difficile da cambiare senza dover fare qualche test unitario. Il test di integrazione è più leggero. Ovviamente vorresti che l'unità testasse qualcosa di molto complesso, ma non è perché l'unità ha testato quella parte, che devi testare l'unità tutto. Ancora una volta vediamo persone che cercano il proiettile d'argento dove non esiste.
Walfrat,

24

Perché dovresti scrivere unit test per controller?

Perché senza conoscere il contesto non si può dire con certezza se è necessario testare questo o quello. Ecco alcuni motivi per cui potresti voler testare i controller:

  • il controller può contenere una logica di cablaggio di servizio complessa, soggetta a errori. I servizi stessi potrebbero funzionare correttamente è il risultato che si desidera testare e per qualche motivo hai considerato di non introdurre il livello di orchestrazione nella tua app
  • i tuoi controller contengono TUTTA la logica di bussiness dell'applicazione e i controller sono in realtà tutto ciò che PUOI testare (per favore non pretendere che tutta la tua vita hai lavorato con basi di codice ideali, ci sono tali basi di codice, credimi)
  • la tua squadra è composta per il 99% da geni e dall'1% di persone medie e tu vuoi mantenere quell'1% di bug nel loro stipendio

2
Vorrei aggiungere: "Non puoi prevedere chi in futuro si sbarazzerà del progetto, e i test fanno parte del codice autocertificato"
Laiv

4
A un certo punto, un progetto che è stato creato senza test in mente potrebbe non essere testabile in altro modo rispetto a un test del controller senza simulazioni. Lavoro con un team C # che ha esattamente un tale progetto nelle loro cure, quindi stanno scrivendo test sui controller fino a quando non possono aggiungere la struttura necessaria (interfacce, ecc.) Per essere in grado di eseguire test più accurati.
Wayne Conrad,

1

Sono completamente d'accordo con l'OP.

Un test unitario per un controller è inutile. Collaudi implicitamente i tuoi controller tramite test di regressione (usando Selenium per esempio).

È necessario TDD tutti i componenti / oggetti utilizzati dal controller e mantenere i controller il più sottili possibile. Quindi tutto è correttamente testato dall'unità. Quello di cui vuoi essere certo è che tutto funziona bene insieme quando si eseguono richieste Web. Questo è il test di regressione.


Forse è così, ma questa non è una risposta alla domanda. In realtà, è un argomento contro l'uso di unit test qui.
JᴀʏMᴇᴇ,

Penso di aver risposto alla domanda "credi che sia necessario un test per questo e perché?"
winkbrace,

Sì, penso che @winkbrace e condivido gli stessi pensieri su questo. Ma credo anche che si tratti di una discussione su cosa dovresti provare unit test e non. Penso che le persone testino troppo e le cose "sbagliate". nel mio esempio, testare il controller dà pochissimo valore poiché è così sottile e si spera abbia test che circondano i servizi. Tutte le risposte qui sono significative e hanno buoni punti, ma non è davvero possibile contrassegnarne una come risposta corretta.
Glassa il

La logica del controller può essere testata utilizzando test di integrazione automatizzati, separati e distinti dai test unitari per i singoli componenti.
KevBurnsJr

-1: un test unitario per un controller potrebbe essere inutile. I controller riguardano la trasformazione, ma a volte la trasformazione stessa è complessa e uno sviluppatore potrebbe desiderare di averla coperta. Penso anche che i test unitari 1) alla fine riguardino la validazione di un'implementazione, non necessariamente la validazione di comportamenti di alto livello, e 2) dovrebbero essere dannatamente veloci . Entrambe le qualità rendono i test unitari molto più utili durante i tempi di implementazione; in altre parole, sono in definitiva uno strumento di sviluppo e, per inciso, un modo per convalidare la qualità del prodotto.
rsenna,
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.