Using multiple arguments in a single layout

I am trying to do this using Mockito in Mock:
When Mock.someMethod (..) is called with argument1 -> return result1
When Mock.someMethod (..) is called with argument2 -> return result2
When Mock.someMethod (..) is called with argument3 -> return result3

when(mock.method(Matchers.argThat(new MyMatcher1() { @Override public boolean matches(Object arg0) { // comparision logic } }))).thenReturn(result1); when(mock.method(Matchers.argThat(new MyMatcher2() { @Override public boolean matches(Object arg0) { // comparision logic } }))).thenReturn(result2); when(mock.method(Matchers.argThat(new MyMatcher3() { @Override public boolean matches(Object arg0) { // comparision logic } }))).thenReturn(result3); 

But Mockito correctly closes the first, but on the second, it throws a NullPointer exception, because for some reason it tries to start Matcher with a zero agent. I am not sure if it is supported.

If this is not the case, how to do it with Mockito? Thanks.

+6
source share
3 answers

At the moment, I managed to get around this problem by getting a zero check in the custom ArgumentMatcher. It worked because NPE only at startup time, when Mockito calls () statements when it executes. It should not even call ArgumentMatcher.matches () at this time! This seems like a bug in Mockito.

+1
source

Instead of recording

 when(mock.method(Matchers.argThat(new MyMatcher1() { @Override public boolean matches(Object arg0) { // comparison logic } }))).thenReturn(result1); 

Try it.

 doReturn(result1).when(mock).method(Matchers.argThat(new MyMatcher1() { @Override public boolean matches(Object arg0) { // comparison logic } })); 

and similarly for result2 and result3 .

This is described in http://docs.mockito.googlecode.com/hg/latest/org/mockito/Mockito.html#12 , but, in my opinion, the documentation is unclear that this design is really necessary in this matter. I will talk with the rest of the Mockito documentation improvement team here.

Good luck.

+13
source

Generally, if the test fails, you should be able to determine what is wrong with the device under test. Avoid writing custom patterns specifically for one test. If a method needs to return more than one value, it is usually sufficient to simply drown out the method, returning the values ​​in the order that the test predicts.

eg.

 when(mock.method(any(Object.class))).thenReturn(result1, result2, result3); 

This will return result 1, the first call, result2 to the second, etc.

There are obviously scenarios where this is not enough, but more often a simpler test is the best.

+4
source

All Articles