Skip to content

JUnit 5 and Mokito

1. Mokito

Mockito empowers developers to create test doubles -- proxy objects that simulate real components -- enabling robust automated unit testing. This makes it an essential tool for test-driven development and a valuable ally in behaviour-driven development.

By isolating a single class for testing, Mockito allows developers to focus precisely on the behavior of that class, while interactions with other classes can be safely represented by lightweight mock objects, without requiring the full system to be operational. This leads to faster, more reliable tests and cleaner, more maintainable code.

Contents

2. Dependancies

Maven dependancis

xml
<dependency>
    <groupId>org.mockito</groupId>
    <artifactId>mockito-core</artifactId>
    <version>5.20.0</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>org.mockito</groupId>
    <artifactId>mockito-junit-jupiter</artifactId>
    <version>5.20.0</version>
    <scope>test</scope>
</dependency>

These two libraries come handy.

  1. mockito-core gives you the mocking abilities.
  2. mockito-junit-jupiter gives you clean, idiomatic support in your JUnit 5 test classes (no need to manually init mocks).

3. Example : mock, when, then

java
import org.junit.Test;
import org.mockito.Mockito;
import static org.junit.Assert.*;
import static org.mockito.Mockito.*;

public class AuthenticatorApplicationTest {

	@Test
	public void testAuthenticate() {
		// Arrange
		AuthenticatorInterface authenticatorMock;
		AuthenticatorApplication authenticator;
		String username = "JavaCodeGeeks";
		String password = "unsafePassword";
		
		authenticatorMock = Mockito.mock(AuthenticatorInterface.class);
		authenticator = new AuthenticatorApplication(authenticatorMock);
		
		when(authenticatorMock.authenticateUser(username, password))
			.thenReturn(false);
		
		// Act
		boolean actual = authenticator.authenticate(username, password);
		
		// Assert
		assertFalse(actual);
	}
	
}

The key part is when we add the behavior, with the when() and thenReturn() functions. Is quite expressive: "When the mock object is called for this method with this parameters, then it returns this value". Note that we are defining the behavior in the mock object, not to the class calling the mock object.

As we are adding the behavior to the reference that has been passed to AuthenticatorApplication instance, it doesn’t matter if we first add the behavior and then we pass the reference, or reverse.

When the AuthenticatorApplication calls to its AuthenticatorInterface, it won’t know what is actually happening, the only thing it knows is just how to deal with the defined interface, which for this case has been designed to return false when it receives "JavaCodeGeeks" and "unsafePassword" as inputs.

Ref: https://www.javacodegeeks.com/wp-content/uploads/2016/09/Mockito-Programming-Cookbook.pdf

4. Verify that method has been called

We can check if a method has been called with certain parameters. For that, we would do something similar to the following:

AuthenticatorApplicationTest.java

java
// ...
verify(authenticatorMock).authenticateUser(username, password);
// ...

To verify that authenticatorMock mock’s authenticateUser method, with username and password parameters.

Apart from checking that the method is actually being called, this verifications are useful to check that the parameters arrive to the method call as they are supposed to arrive. So, for example, if you run the test with the following verification:

AuthenticatorApplicationTest.java

java
// ...
verify(authenticatorMock).authenticateUser(username, "not the original password");
// ...

The test will fail.

Ref: https://www.javacodegeeks.com/wp-content/uploads/2016/09/Mockito-Programming-Cookbook.pdf

4.1. Verify interactions and stub method calls

Verifying interactions..

java
import static org.mockito.Mockito.*;

// mock creation
List mockedList = mock(List.class);
// or even simpler with Mockito 4.10.0+
// List mockedList = mock();

// using mock object - it does not throw any "unexpected interaction" exception
mockedList.add("one");
mockedList.clear();

// selective, explicit, highly readable verification
verify(mockedList).add("one");
verify(mockedList).clear();

and stub method calls

java
// you can mock concrete classes, not only interfaces
LinkedList mockedList = mock(LinkedList.class);
// or even simpler with Mockito 4.10.0+
// LinkedList mockedList = mock();

// stubbing appears before the actual execution
when(mockedList.get(0)).thenReturn("first");

// the following prints "first"
System.out.println(mockedList.get(0));

// the following prints "null" because get(999) was not stubbed
System.out.println(mockedList.get(999));

Ref: https://site.mockito.org/

4.2. Verify that method has been called n times

Apart from checking that the method has been called or not, we have many possibilities regarding to number of method calls.

Let’s see how we can do it:

AuthenticatorApplicationTest.java

java
// ...
verify(authenticatorMock, times(1)).authenticateUser(username, password);
verify(authenticatorMock, atLeastOnce()).authenticateUser(username, password);
verify(authenticatorMock, atLeast(1)).authenticateUser(username, password);
verify(authenticatorMock, atMost(1)).authenticateUser(username, password);
// ...

As you can see, we have different notations available to make the verifications: specifying the number of times that the mocking method should be called, how much times should be called at least, and how much at most.

As in the previous example, the verifications are made for the exact parameters that the mocking method uses.

We can also verify that the method has never been called:

AuthenticatorApplicationTest.java

java
// ...
verify(authenticatorMock, never()).authenticateUser(username, password); // This will make the test fail!
// ...

Which, actually, is equivalent to times(0), but would be more expressive when we really want to verify that a method has never been called.

Ref: https://www.javacodegeeks.com/wp-content/uploads/2016/09/Mockito-Programming-Cookbook.pdf

5. More info

Main reference documentation features:

  • mock()/@Mock: create mock
    • optionally specify how it should behave via Answer/MockSettings
    • when()/given() to specify how a mock should behave
    • If the provided answers don’t fit your needs, write one yourself extending the Answer interface
  • spy()/@Spy: partial mocking, real methods are invoked but still can be verified and stubbed
  • @InjectMocks: automatically inject mocks/spies fields annotated with @Spy or @Mock
  • verify(): to check methods were called with given arguments
    • can use flexible argument matching, for example any expression via the any()
    • or capture what arguments were called using @Captor instead
  • Try Behavior-Driven development syntax with BDDMockito
  • Use Mockito on Android, thanks to the team working on dexmaker

Ref: https://site.mockito.org/

6. Remember... !!

  • Do not mock types you don’t own
  • Do not mock value objects
  • Do not mock everything
  • Show love with your tests!

Click here for more documentation and examples. All documentation lives in javadocs so you don’t need to visit that page too often. There is also a RefCard.

If you have suggestions, find documentation unclear, or find a bug, write to our mailing list. You can report feature requests and bugs in GitHub.

Ref: https://site.mockito.org/

7. References

How to write good tests · mockito/mockito Wiki · GitHub https://github.com/mockito/mockito/wiki/How-to-write-good-tests

Mockito framework site https://site.mockito.org/

Mockito Programming Cookbook https://www.javacodegeeks.com/wp-content/uploads/2016/09/Mockito-Programming-Cookbook.pdf

Mockito vs EasyMock · mockito/mockito Wiki · GitHub https://github.com/mockito/mockito/wiki/Mockito-vs-EasyMock

© 2023-2025 Maduranga Kannangara. Feel free to use or share this content. Attribution is appreciated but not required.