Reputation: 4111
Does java.util
Optional.ofNullable
works properly with Mockito?
During the code execution I encounter something like this:
User user = Optional.ofNullable(userProviderMock.findUser()).orElse(someMethod())
I set my mock behaviour like following:
when(userProviderMock.findUser()).thenReturn(new User());
When I run it, userProviderMock
returns new User()
(debug confirms that), but somehow someMethod()
is still executed.
I have literally no idea why this is happening. Any clues?
Upvotes: 3
Views: 5869
Reputation: 183484
Mockito and ofNullable
aren't really at issue here. Consider this code:
Optional.of("foo").orElse(someMethod())
The above code will evaluate to Optional.of("foo")
— but it still calls orElse
, so it still has to call someMethod()
in order to pass its return-value as an argument to orElse
, even though that argument ends up not being used.
If this is a problem for you — if you don't want someMethod()
to be called unless its return-value is actually needed — then you should use orElseGet
instead:
Optional.of("foo").orElseGet(() -> someMethod())
or rather:
User user = Optional.ofNullable(userProviderMock.findUser()).orElseGet(() -> someMethod())
Edited to add: Didier L points out that () -> someMethod()
can also be written as this::someMethod
(that is: we can write it as a method reference rather than a lambda), which is probably more readable.
Either way, it gets converted implicitly to approximately this:
User user = Optional.ofNullable(userProviderMock.findUser()).orElseGet(new Supplier<User>() {
public User get() {
return someMethod();
}
});
Upvotes: 8