Mockito - difference between doReturn () and when ()

I am currently using Mockito to fake service-level objects in a Spring MVC application in which I want to test my controller methods. However, as I read about the specifics of Mockito, I found that the doReturn(...).when(...) methods are equivalent to when(...).thenReturn(...) . So my question is that you need to have two methods that do the same thing, or what is the subtle difference between doReturn(...).when(...) and when(...).thenReturn(...) ?

Any help would be appreciated.

+69
java unit-testing mockito
Dec 03 '13 at 14:28
source share
6 answers

Two syntaxes for stubbing are roughly equivalent. However, you can always use doReturn/when for stubbing; but there are times when you cannot use when/thenReturn . One such method is stubbing void. Others include using Mockito with spies and executing the same method once.

One thing that when/thenReturn gives you is that doReturn/when does not perform type checking on the return value at compile time. However, I believe that this is almost irrelevant - if you have the wrong type, you will find out as soon as you run the test.

I highly recommend using only doReturn/when . It makes no sense to learn two syntaxes when they will do.

You can refer to my answer in Mockito Formation "grammars" - a more detailed answer to a very close question.

+93
Dec 03 '13 at 19:48
source share

Both approaches behave differently if you use a spied object (annotated using @Spy ) instead of a layout (annotated using @Mock ):

  • when(...) thenReturn(...) makes a real method call before returning the specified value. Therefore, if the called method throws an exception, you must deal with it / mock it, etc. Of course, you still get your result (what you define in thenReturn(...) )

  • doReturn(...) when(...) does not call the method at all .

Example:

 public class MyClass { protected String methodToBeTested() { return anotherMethodInClass(); } protected String anotherMethodInClass() { throw new NullPointerException(); } } 

Test:

 @Spy private MyClass myClass; // ... // would work fine doReturn("test").when(myClass).anotherMethodInClass(); // would throw a NullPointerException when(myClass.anotherMethodInClass()).thenReturn("test"); 
+92
Apr 01 '15 at 15:12
source share

The latter alternative is used for methods on mocks that return void .

Please see, for example, here: How to make mockito void methods with mockito

+3
Dec 03 '13 at 14:39
source share

We continue this answer . There is another difference: if you want your method to return different values, for example, when it was first called, called the second time, etc., then you can pass values, for example, ...

 PowerMockito.doReturn(false, false, true).when(SomeClass.class, "SomeMethod", Matchers.any(SomeClass.class)); 

That way, it will return false when the method is called in one test case, and then it will return false again and finally true.

+1
Nov 28 '16 at 2:48
source share

Mockito javadoc seems to say why use doReturn() instead of when() Use doReturn () on those rare occasions when you cannot use Mockito.when (Object).

Beware that Mockito.when (Object) is always recommended for trimming because it is an argument of type safe and more readable (especially when consecutive calls).

Here are those rare cases where doReturn () is suitable:

1. When spying on real objects and calling real methods on spies, effects

List list = new LinkedList(); List spy = spy(list);

// Impossible: the real method is called spy.get (0) throws IndexOutOfBoundsException (the list is not populated yet)

when(spy.get(0)).thenReturn("foo");

// You must use doReturn () for stubbing: doReturn("foo").when(spy).get(0);

2. Overriding the previous exception:

when(mock.foo()).thenThrow(new RuntimeException());

// Impossible: the foo () method thrown for an exception is called the RuntimeException. when(mock.foo()).thenReturn("bar");

// You must use doReturn () for stubbing:

doReturn("bar").when(mock).foo(); The above scenarios show a compromise on the elegant Mockito syntax. Note that scripts are very rare, though. Espionage should be sporadic, and an exclusive exception is very rare. Not to mention that overall reinstallation is a potential smell of code that indicates too many knocks.

+1
Jan 31 '17 at 18:19
source share

"mock" can mimic an object instead of creating it, "spy" can create an actual object with actual parameters. When we do a unit test, we often use them. But 'when (xxx) .thenReturn (xxx)' is used for mock and 'doReturn (xxx) .when (xxx)' is used for spy.

-one
Sep 06 '16 at 9:33
source share



All Articles