DEV Community

loading...

Mockito: Passing in any() and a literal to the same method

arsenalist profile image Zarar Siddiqi ・1 min read

Mockito has a restriction where when using Mockito.when(someMethod(...)) you can't pass in a combination of any() and literal values to someMethod().It complains that we have to pick one. So, the following is illegal:

Solution 1 (preferred and as shown by Stephen):

Mockito.when(context.configFileProvider(eq("file1"), any())).thenReturn("file1_contents")

Solution 2 (works but ugly and the original post here):

Mockito.when(context.configFileProvider("file1", any())).thenReturn("file1_contents")

There is a way around it which I stumbled upon when trying to test nested closures while writing Groovy scripts for Jenkins (don't ask me). Here it is:

    Mockito.when(context.configFileProvider(Mockito.any(), Mockito.any())).thenAnswer(
        new Answer<String>(){
            @Override
            String answer(InvocationOnMock invocation){
                List arg1 = invocation.getArgument(0)
                switch (arg1.get(0)) {
                    case "file1": return "file1_contents"
                }
            }
        }
    );

This is logically equivalent to the previous statement.

Discussion (5)

pic
Editor guide
Collapse
nutterzuk profile image
Stephen Nutbrown • Edited

Can you not just use:
Mockito.when(context.configFileProvider(eq("file1"), any())).thenReturn("file1_contents") ?

It's that you can't pass in a literal and a matcher; that's the limitation. eq is matcher, and any() is a matcher, and so using these together would be fine. Then you don't need this workaround.

Collapse
arsenalist profile image
Zarar Siddiqi Author • Edited

Wow - that is such a more elegant way of doing this. Thank you! I've updated the post.

Collapse
nutterzuk profile image
Stephen Nutbrown • Edited

No worries Zarar. Another thing you might consider doing is statically importing Mockto.when, that way you don't need to keep having "Mockito." in your tests. In a similar way that most people would statically import assertThat. Hope it helps!

Thread Thread
arsenalist profile image
Zarar Siddiqi Author

Yes, I definitely do that. How many uses of an assert statement do you generally wait for before doing the static import? I think I wait for about three.

Thread Thread
nutterzuk profile image
Stephen Nutbrown

I usually do it straight away for mockito and junit methods. The reason being that although it may not be necessary in that class, generally across the project you'll be using mockito and junit in every test class, so it becomes a norm. It's a bit off if you have some tests statically importing it and others not, so realising that I'm going to use it a lot, I just go for it :).