W trakcie pisania kodu przyzwyczailiśmy się już do tego, że należy równolegle pisać testy. Podejść, kiedy i jak pisać testy jest wiele. Do wyboru mamy też kilka dostępnych frameworków testowych, ale nie o tym chciałem napisać. W tym artykule chcę poruszyć temat badania pokrycia kodu testami.W trakcie pisania testów niejednokrotnie występuje potrzeba sprawdzenia, które fragmenty kodu pokryte są testami, a które nie. Taka informacja pozwala na napisanie dodatkowych testów, które pokryją ten fragment kodu niepokryty testami. W przyszłości pozwoli to na uniknięcie błędów.

Zdania te brzmią fajnie, ale problem pojawia się z narzędziami. Większość narzędzie jest płatna. Powoduje to, że nie nadają się do użytku domowego. Użytkownika domowego nie stać na takie programy. Pewnego rodzaju kompromisem są programy firmy JetBrains. W przypadku, gdy tworzymy aplikację typu OpenSource to można uzyskać ich programy za darmo. Jeżeli spełniamy ten warunek to możemy użyć programu dotCover. Jeśli nie to pozostaje nam szukać innego rozwiązania.

Jeden z wieczorów poświęciłem na poszukiwania i znalazłem program, który:

  • testuje pokrycie kodu,
  • pokazuje, które linijki są wykonywane, a które nie,
  • jest darmowy.

Czyli nadaje się w sam raz do użytku domowego. Tym programem jest PartCover. Przy pierwszym uruchomieniu można zauważyć bardzo skromny interfejs. Ale jest on aż nadto wystarczający.

PartCover - Okno główne programu

Zanim udało mi się uzyskać poprawny wynik testów potrzebowałem trochę poprzeglądać Internet. Niby w konfiguracji nie ma nic szczególnego, ale jednak są drobne niuanse, w przypadku zastosowania MSTest jako frameworka testującego.

Przechodząc do rzeczy, aby uzyskać interesujące nas wyniki należy skonfigurować program. W tym celu wchodzimy do File, a następnie wybieramy Run Target. W tym momencie zostanie wyświetlone następujące okno:

Konfiguracja programu - PartCover

W tym oknie musimy uzupełnić:

  • Executable File – podajemy tu ścieżkę do frameworka testowego, w przypadku MSTest.exe i Visual Studio 2010 jest to: C:\Program Files\Microsoft Visual Studio 10.0\Common7\IDE\MSTest.exe. W trakcie szukania informacji jak poprawnie skonfigurować ten program znalazłem też informację, że jeśli użyte jest jakieś narzędzie do Mocków (np. Typemock Isolator), które wymaga wcześniejszego uruchomienia to w tym miejscu należy wpisać ścieżkę do niego, a ścieżkę do frameworka umieścić w Working Arguments,
  • Working Directory – ścieżka do katalogu ze skompilowanymi testami,
  • Working Arguments – należy tu podać plik dll zawierający testy,
  • Rules – w tym miejscu można zdefiniować, które klasy, przestrzenie nazw będą sprawdzane, a które nie.

Dalszego komentarza wymagają dwa pola: Working Arguments i Rules. Pierwsze pole oraz wybór MSTest.exe jako silnika do testowania spowodowało, że musiałem poświęcić trochę czasu na zaznajomienie się z tym narzędziem. W przypadku NUnita ten problem nie występuje i zaraz po wpisaniu wartości bez dodatkowych parametrów program działa. W przypadku MSTest.exe w tym wierszu należy dodać /testcontainer: przez plikiem z testami oraz /noisolation zaraz po nim. Dodatkowo ważna jest kolejność. W przypadku jej nie zachowania program nie zwróci poprawnych wyników – pokrycie kodu będzie wynosiło 0%.

Drugie pole Rules pozwala na zdefiniowanie swoistego rodzaju filtrowania. Jeżeli chcemy, aby jakaś klasa została wzięta do raportu pokrycia należy posłużyć się notacją +filtr. W przeciwnym wypadku należy użyć -filtr. Aby uruchomić to narzędzie musimy zdefiniować, przynajmniej jeden filtr. Najprostszym filtrem jest +[*]*, który bierze wszystkie wyniki do raportu pokrycia.

Pewną nieścisłością w stosunku do przyjętych standardów UI jest miejsce zapisywania „projektu”. W większości narzędzie robi się to w menu File. W tym przypadku należy to zrobić z poziomu tego okna. W menu File w programie nie ma takiej opcji.

Mając już skonfigurowany program można przejść do jego uruchomienia. W tym celu należy kliknąć przycisk Start. W tym momencie zostaną uruchomione testy. Po chwili w programie będzie można zobaczyć wyniki pokrycia kodu. Aby zobaczyć, które linijki kodu są wykonywane w trakcie testów, a które nie należy z menu View wybrać polecenie View Coverage Details. Teraz klikając na nazwy klas można zobaczyć, które linijki są wykonywane (kolor zielony), a które nie (kolor czerwony).

Wyniki pokrycia - PartCover

Dodatkową zaletą tego narzędzia jest fakt, że można uruchomić z konsoli. Dzięki temu można go zintegrować z systemem automatycznych buildów.

set partcover="C:\Program Files (x86)\Gubka Bob\PartCover .NET 2.3\partcover.exe"
set nunit="C:\Program Files (x86)\NUnit 2.5.3\bin\net-2.0\nunit-console-x86.exe"
set tests="Debug\YourTests.dll"
%partcover% --target %nunit% --target-args %tests% --include [*]* --output PartCoverResults.xml

Kolejną dosyć przydatną funkcją jest licznik odwiedzin danego fragmentu kodu. Nad oknem pokazującym, które elementy zostały wykonane jest tabela z informacją, mówiącą ile razy dany kawałek kodu był wykonywany. Aby zlokalizować miejsce w kodzie, do którego dana linijka się odnosi wystarczy na nią kliknąć.

Analizując wyniki należy pamiętać o tym, że 100% pokrycie kodu nie oznacza poprawne przetestowanie klasy, metody. Informacja ta mówi nam jedynie tyle, że dany kod został przynajmniej raz uruchomiony.