Nasza strona używa cookies. Korzystając ze strony, wyrażasz zgodę na używanie cookies, zgodnie z aktualnymi ustawieniami przeglądarki. Rozumiem

Mockito – czyli jak wycisnąć cytrynę, której nie mamy

Sprawdź, jak korzystać z Mockito, czyli frameworka Javy, ułatwiającego pisanie testów jednostkowych.

Czym jest Mockito? Nie, nie mam na myśli zielonkawego napoju z palemką. Mam na myśli narzędzie Javy ułatwiające pisanie testów jednostkowych. Jak sama nazwa wskazuje, narzędzie to (a właściwie framework), pozwala tworzyć mocki, łatwo i przyjemnie.


Czym są tajemnicze mocki?

Można je porównać do manekinów podczas testów zderzeniowych aut. Dzięki nim możemy testować wywierane na nie siły i testować bezpieczeństwo samochodów, bez poświęcania żywych ludzi.

Mocki z kolei pozwalają na stworzenie atrapy obiektu i bezpieczne obserwowanie zachowania w testowanej sytuacji, z uwzględnieniem relacji między różnymi obiektami. A to wszystko bez konieczności uruchamiania rzeczywistej implementacji.

Przykładowo testując aplikację do nawigacji w terenie, możemy stworzyć mocka usługi pobierającej aktualną pozycję z GPS. Dzięki temu, nie musimy mieć łączności z satelitą, ba nie musimy się przemieszczać, aby testować aplikację w różnych lokalizacjach. Nasz mock, będzie zwracał symulowaną pozycję GPS, która posłuży do testowania serwisu do nawigacji.

W analogiczny sposób możemy testować aplikację bazodanową, udając serwis bazy danych, aplikację komunikującą się z Internetem, udając serwis dostępu do Internetu lub po prostu symulując nieistniejącą jeszcze implementację interfejsu.


Czym jest Mockito?

Mockito pozwala na banalnie proste tworzenie mocków i weryfikację wywieranych na nie oddziaływań.

Framework Mockito został doceniony przez społeczność Stack Overflow jako najlepsza biblioteka do tworzenia mocków, znalazł się także w rankingu 10 najpopularniejszych bibliotek wykorzystywanych w projektach zgromadzonych GitHub. Dowodzi to cenności narzędzia.

Stwórzmy zatem przykład w oparciu o wspomnianą nawigację GPS i komponenty Spring, aby zademonstrować wykorzystanie Mockito.


Nasz komponent ma za zadanie zwracać dystans określający odległość pomiędzy dwoma ostatnimi odczytami położenia geograficznego z GPS.  Odległość jest zwracana za pomocą metody getDistance(). Podczas inicjowania komponentu uruchamiamy usługę GPS i pobieramy bieżącą lokalizację. Przy wywołaniu metody getDistance() pobieramy bieżącą lokalizację i obliczamy odległość pomiędzy kolejnymi odczytami z wykorzystaniem biblioteki Geodesy.

Dodatkowo tworzymy interfejs, aby móc łatwo podmieniać implementacje usługi GPS i stworzyć mocka symulującego działanie GPS.


Aby przetestować działanie klasy Navigation, musimy stworzyć mocka interfejsu GpsService. Na początek dodajemy zależności do pom.xml.

Biblioteka Mockito:


Biblioteka testów Spring Boot wraz z zależnościami (junitassertj, ...)


W dalszej kolejności piszemy test jednostkowy:


Podczas startu testu tworzony jest obiekt, który implementuje interfejs GpsService. Obiekt domyślnie zawiera puste implementacje metod, które zwracają null.

Musimy zatem określić jego zachowanie poprzez metodę when().


Powyższy fragment kodu należy rozumieć następująco:

zwróć kolejną pozycję z listy rozpoczynając od pierwszej - każde kolejne wywołanie zwróci kolejną.

Jeśli na liście byłaby tylko jedna pozycja - zwrócona zostałaby zawsze ta sama.

Pierwszą pozycję pobieramy podczas inicjowania GPS, kolejną podczas wywołania navigation.getDistance(). W ten sposób możemy symulować zachowania wielu różnych interfejsów, bez konieczności tworzenia lub uruchamiania ich implementacji.

Mockito zawiera wiele mechanizmów weryfikacji oddziaływania na mock. Jedną z nich jest weryfikacja ilości wywołań metody z mocka.


W powyższym przypadku weryfikujemy, czy metoda getCurrentLocation została dokładnie 2 razy wywołana z dowolnym parametrem typu double.  Jeśli będzie inaczej, test się nie powiedzie.

Analogicznie możemy zweryfikować, czy getCurrentLocation zostanie wywołana z konkretną wartością parametru, stosując metodę Mockito.eq:


Można też zastosować bardziej zaawansowaną weryfikację z wykorzystaniem ArgumentCaptor:


Tworzymy obiekt przechwytujący argumenty wywołania dla klasy zgodnej z typem argumentu.

Weryfikujemy, czy metoda getCurrentLocation została wywołana dokładnie 2 razy, zbierając przy okazji parametry wywołania w naszym obiekcie przechwytującym.


Mając przechwycone parametry wywołania, możemy zweryfikować ich zgodność z założeniami. W tym przypadku podczas 2 wywołań oczekujemy, że argument wywołania będzie posiadał cały czas tę samą wartość równą 0.6.


W podobny sposób zamiast tworzyć typowy mock na podstawie interfejsu, można stworzyć obiekt typu spy na podstawie rzeczywistej klasy. W obiektach typu spy wykorzystujemy realną implementację, w której możemy symulować zachowanie wybranych metod, a dla pozostałych zachować istniejącą implementację. W poniższym przykładzie zamiast interfejsu GpsService tworzymy atrapę na bazie rzeczywistej implementacji klasy GpsServiceImpl (która implementuje interfejs GpsService). W ten sposób, możemy zrezygnować z użycia Mockito.when, czyli konieczności określania zachowania, które badamy.


To oczywiście tylko niektóre z możliwości frameworka Mockito. Pozostałe zostały opisane w oficjalnej dokumentacji.

Zobacz kogo teraz szukają