Test unitari per codice C ++ - Strumenti e metodologia [chiuso]


134

Sto lavorando su un grande sistema c ++ che è in sviluppo da alcuni anni. Nell'ambito di uno sforzo per migliorare la qualità del codice esistente, ci siamo impegnati in un grande progetto di refactoring a lungo termine.

Conosci un buon strumento che può aiutarmi a scrivere unit test in C ++? Forse qualcosa di simile a Junit o Nunit?

Qualcuno può dare qualche buon consiglio sulla metodologia di scrittura di unit test per moduli che sono stati scritti senza in mente unit test?


1
Dai un'occhiata a questa domanda: stackoverflow.com/questions/3150/…
Aardvark,

Risposte:


83

L'applicazione dei test unitari al codice legacy è stata la vera ragione per cui è stato scritto Lavorare in modo efficace con il codice legacy . Michael Feathers è l'autore - come menzionato in altre risposte, è stato coinvolto nella creazione di CppUnit e CppUnitLite .

testo alternativo


4
Aggiunta una miniatura: votata. Il libro aiuta più di ogni altro strumento.
Gishu,

2
Penso che CPPUnit potrebbe rendere più semplice la scrittura di test. Usiamo CPPUnit, ma non sono soddisfatto. Devo aggiornare due file per ogni test e, a mio avviso, un test dovrebbe essere semplice da scrivere come: 'TEST ("testname") {ASSERT (1 == 1);}' Il libro invece è un must per tutti, non solo quelli che lavorano con il codice legacy, ma anche per quelli che lo creano;)
daramarak

9
Da quando è ereditato il c ++ ?!
Nils,

9
Non è che il C ++ sia legacy - se ricordo bene, quel libro definisce un progetto legacy come uno per il quale non ci sono, o pochissimi test unitari. Tali progetti tendono ad essere / difficili / in cui scrivere test unitari, poiché lo sviluppo guidato dai test non ha mai influenzato la base di codice in modo che sia banale scriverli.
Arafangion

7
@Nils: Come menziona uno dei revisori Amazon del libro, "il codice legacy è un codice senza unit test", che è esattamente ciò di cui tratta questa domanda.
David Johnstone,

40

Google ha recentemente rilasciato la propria libreria per le app C ++ di unit testing, denominata Google Test.

Progetto su Google Code


1
è possibile usarlo con VC ++
yesraaj

Sembra abbastanza bene, specialmente il modo in cui devono aggiungere una descrizione a ciascuna asserzione. Sul lato negativo, personalmente preferisco avere una classe Unit Test invece delle macro che in realtà non sembrano classi.
Wernight,

3
un altro punto interessante sono le possibilità di derisione: code.google.com/p/googlemock
Philipp

Trovo questo MOLTO più bello di CPPUNIT che richiede tonnellate di macro e file magici per far funzionare i test
paulm

30

Dai un'occhiata a un eccellente confronto tra diverse suite disponibili. L'autore di quell'articolo ha successivamente sviluppato UnitTest ++ .

Ciò che mi piace particolarmente al riguardo (a parte il fatto che gestisce bene le eccezioni ecc.) È che c'è una quantità molto limitata di "amministrazione" attorno ai casi di test e alla definizione dei dispositivi di test.


2
Non è questo il nostro errore fondamentale? Ha una buona conoscenza dei progetti disponibili, ma invece di migliorarli, inizia i suoi.
Peter

@peterchen: si; ma poi UnitTest ++ è così piccolo e leggero che ha valore nell'essere un progetto separato - è molto facile da mettere in funzione.
TimStaley,

24

Boost ha una libreria di test che contiene il supporto per i test unitari. Potrebbe valere la pena dare un'occhiata.


4
Posso consigliare questo eccellente toolkit.
Rob,

1
Sì, boost è la strada da percorrere. Nessun sovraccarico, prova e vai! In realtà stavo lavorando sul mio quadro nella disperazione quando la spinta è arrivata in mio soccorso. Grazie boost (per tutto!)
daramarak


21

Noel Llopis di Games From Within è l'autore di Exploring the C ++ Unit Testing Framework Jungle , una valutazione completa (ma ora datata) dei vari framework C ++ Unit Testing, nonché un libro sulla programmazione di giochi.

Ha usato CppUnitLite per un po ', risolvendo varie cose, ma alla fine ha unito le forze con un altro autore di librerie di test unitari e ha prodotto UnitTest ++ . Usiamo UnitTest ++ qui, e mi piace molto, finora. Ha (per me) l'esatto giusto equilibrio di potenza con un ingombro ridotto.

Ho usato soluzioni nostrane, CxxTest (che richiede Perl) e boost :: test. Quando ho implementato i test unitari qui nel mio lavoro attuale, è praticamente arrivato a UnitTest ++ vs boost :: test.

Mi piacciono molto la maggior parte delle librerie di boost che ho usato, ma IMHO, boost :: test è un po 'troppo pesante. Soprattutto non mi è piaciuto che tu abbia richiesto (AFAIK) di implementare il programma principale del cablaggio di test usando una macro boost :: test. So che non è un TDD "puro", ma a volte abbiamo bisogno di un modo per eseguire test dall'interno di un'applicazione GUI, ad esempio quando un flag di test speciale viene passato sulla riga di comando e boost :: test non può supportare questo tipo di scenario.

UnitTest ++ è stato il framework di test più semplice da configurare e utilizzare che ho riscontrato nella mia (limitata) esperienza.


17

Sto usando l'eccellente libreria Boost.Test insieme a una libreria Turtle molto meno conosciuta ma davvero incredibile : una libreria di oggetti finti basata su boost.

Poiché un esempio di codice parla meglio delle parole, immagina di voler testare un calculatoroggetto che funzioni su viewun'interfaccia (che è l'esempio introduttivo di Turtle):

// declares a 'mock_view' class implementing 'view'
MOCK_BASE_CLASS( mock_view, view )
{
    // implements the 'display' method from 'view' (taking 1 argument)
    MOCK_METHOD( display, 1 )                   
};

BOOST_AUTO_TEST_CASE( zero_plus_zero_is_zero )
{
    mock_view v;
    calculator c( v );

    // expects the 'display' method to be called once with a parameter value equal to 0
    MOCK_EXPECT( v, display ).once().with( 0 ); 

    c.add( 0, 0 );
}

Vedi quanto è facile e dettagliato dichiarare le aspettative sull'oggetto finto? Ovviamente, il test fallisce se le aspettative non sono soddisfatte.


14

Ho appena spinto il mio framework, CATCH , là fuori. È ancora in fase di sviluppo, ma credo che superi già la maggior parte degli altri framework. Persone diverse hanno criteri diversi, ma ho cercato di coprire gran parte del terreno senza troppi compromessi. Dai un'occhiata al mio post sul blog collegato per un assaggio. Le mie cinque caratteristiche principali sono:

  • Solo intestazione
  • Registrazione automatica di test basati su funzioni e metodi
  • Decompone le espressioni C ++ standard in LHS e RHS (quindi non è necessaria un'intera famiglia di assert macro).
  • Supporto per sezioni nidificate all'interno di un dispositivo basato su funzioni
  • Test dei nomi con linguaggio naturale: vengono generati nomi di funzioni / metodi

Ha anche attacchi Objective-C.


4
doctest è la mia reimplementazione di Catch con un'enorme attenzione alla velocità di compilazione - controlla le FAQ per vedere come sono diverse
onqtam




6

Attualmente sto cercando un test unitario e un framework simulato che possa essere utilizzato nella nostra azienda per una lunga base di codice. Come sapete, l' elenco dei framework di unit test per c ++ è lungo, quindi ho applicato alcuni filtri per ridurlo a una mano piena che può essere esaminata più da vicino. Il primo criterio di filtro era che doveva essere gratuito. Il secondo criterio era l'attività del progetto. Ho anche cercato quadri beffardi perché ne hai bisogno se vuoi scrivere unit test.

Mi è venuta in mente la seguente lista (approssimativamente) ordinata per attività, la più alta attività in alto:

  • GoogleTest / GoogleMock: molti collaboratori e utilizzati da Google stesso. Questo sarà probabilmente qui per qualche tempo e riceverà aggiornamenti. Per la mia base di codice privata passerò a questa combinazione nella speranza di saltare sul treno più veloce.

  • BoostTest + Turtle: non aggiornato spesso, ma il framework di test fa parte del boost, quindi dovrebbe essere mantenuto. D'altra parte, la tartaruga è mantenuta principalmente da un ragazzo, ma ha un'attività risentita, quindi non è morta. Ho fatto quasi tutta la mia esperienza di test con questa combinazione perché abbiamo già utilizzato la libreria boost nel mio lavoro precedente e attualmente la utilizzo per il mio codice privato.

  • CppUTest: fornisce test e derisione. Questo progetto è stato attivo dal 2008 al 2015 e ha un'attività piuttosto recente. Questa scoperta è stata una piccola sorpresa perché molti progetti con attività significativamente inferiori si presentano più spesso durante le ricerche sul Web (come CppUnit che ha avuto il suo ultimo aggiornamento nel 2013). Non ho approfondito questo aspetto, quindi non posso dire nulla dei dettagli. Modifica (16.12.2015): Di recente ho provato questo e ho trovato questo quadro un po 'goffo e "alla moda", specialmente quando usavo le classi simulate. Inoltre sembrava avere una minore varietà di affermazioni rispetto ad altri quadri. Penso che il suo principale punto di forza sia che può essere utilizzato con progetti C puri.

  • QTest: la libreria di test fornita con il framework Qt. La manutenzione dovrebbe essere garantita per qualche tempo, ma la uso piuttosto come libreria di supporto, perché la registrazione del test è IMO più goffa rispetto ad altri framework. Per quanto ho capito, ti costringe ad avere un ex-test per ogni dispositivo di test. Ma le funzioni dell'helper di test possono essere utili durante il test del codice Qt-Gui. Non ha beffe.

  • Cattura: ha un'attività recente ma è principalmente sviluppata da un ragazzo. La cosa bella di questo framework è l'approccio di fixture alternativo che ti permette di scrivere il codice di fixture riutilizzabile nel test stesso. Inoltre, consente di impostare i nomi dei test come stringhe, il che è utile quando si tende a scrivere intere frasi come nomi di test. Vorrei che questo stile fosse strappato e messo in googleTest ;-)

Quadri finti

Il numero di framework simulati è molto più piccolo del numero di framework di test, ma qui ci sono quelli che ho scoperto di avere attività recenti.

  • Hippomock : attivo dal 2008 ora ma solo a bassa intensità.

  • FakeIt : attivo dal 2013 unitl ora ma più o meno sviluppato da un ragazzo.

Conclusione

Se la tua base di codice è attiva a lungo termine, scegli tra BoostTest + Turtle e GoogleTest + GoogleMock . Penso che quei due avranno una manutenzione a lungo termine. Se hai solo una base di codice di breve durata puoi provare Catch che ha una bella sintassi. Quindi dovresti scegliere anche un quadro beffardo. Se lavori con Visual Studio puoi scaricare gli adattatori del test runner per BoostTest e GoogleTest, che ti permetteranno di eseguire i test con la GUI del test runner integrata in VS.


3

Vedi anche le risposte alla domanda strettamente correlata "La scelta di uno strumento / framework di test delle unità c ++", qui


3

C'è anche TUT , Template-Unit-Test, un framework basato su template. La sua sintassi è scomoda (alcuni lo hanno definito abuso di modelli), ma il suo principale vantaggio è che è tutto contenuto in un singolo file di intestazione .

Qui troverai un esempio di unit test scritto con TUT .


2
Ho creato una libreria solo intestazione che fornisce macro che avvolgono TUTs assicurano la funzione e testano il codice di declerazione sia per semplificarlo che per fornire informazioni su file e numeri di riga in caso di errori. Ecco un link a un post con esempi della differenza nell'output e nel codice, nonché un link al progetto su github: codecrafter.wordpress.com/2012/12/19/tutadapter1
Josh Heitzman

2

Ho provato CPPunit e non è molto facile da usare.

L'unica alternativa che conosco è usare C ++. NET per racchiudere le tue classi C ++ e scrivere test unitari con uno dei framework .NET unit testing (NUnit, MBUnit ecc.)



1

Michael Feathers di ObjectMentor è stato determinante nello sviluppo di CppUnit e CppUnitLite.

Ora raccomanda CppUnitLite



1

Dai un'occhiata a cfix ( http://www.cfix-testing.org ), è specializzato per lo sviluppo di Windows C / C ++ e supporta sia i test delle unità in modalità utente che kernel.


Grazie per la condivisione. Di recente ho iniziato a utilizzare cfix a scopo di test. Stavo cercando un modo per visualizzare lo stack di chiamate sia in caso di test passati che falliti. C'è modo in cfix per raggiungere questo obiettivo?
tryToLearn

1

Se usi Visual Studio 2008 SP1, ti consiglio vivamente di utilizzare MSTest per scrivere i test unitari. Quindi uso Google mock per scrivere le beffe. L'integrazione con l'IDE è l'ideale e consente e non comporta il sovraccarico di CPPunit in termini di modifica di tre posizioni per l'aggiunta di un test.


1

Penso che VisualAssert stia facendo un ottimo lavoro nell'integrazione VS. Ti consente di eseguire ed eseguire il debug dei test da VS e non è necessario creare un eseguibile per eseguire i test.



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.