Question

I would like to capture the argument inputMessage in the readInternal() of the CustomMessageConverter class when client submits a message. client object here is not a mock object.

@Component
public class CustomMessageConverter extends AbstractHttpMessageConverter<Object> {

...

    @Override
    protected Object readInternal(final Class<? extends Object> clazz, final HttpInputMessage inputMessage) throws IOException,
            HttpMessageNotReadableException {

            ...do something here...
    }
...
}

In AbstractHttpMessageConverter class:

@Override
public final T read(Class<? extends T> clazz, HttpInputMessage inputMessage) throws IOException {
    return readInternal(clazz, inputMessage);
}

So, I wrote a mockito class to capture it.

But, it is still going to the regular converter class. Could you suggest what I am doing wrong?

@Mock
CustomMessageConverter mockMessageConverter;

@Captor
private ArgumentCaptor<HttpInputMessage> inputMessage;


@Test
public void test() {
    when(mockMessageConverter.read(CustomMessage.class, inputMessage.capture())).thenReturn(null);
    client.submitMessage(Message);
    verify(mockMessageConverter, times(1));
    Object actual = customConverter.read(CustomMessage.class, inputMessage.getValue());
}
Was it helpful?

Solution

Per the limitations of Mockito, you can't stub or verify final methods. In short, because the method is marked final, Java skips looking up the method in a method table (or calling the Proxy object that Mockito creates) and compiles in a call to the method implementation directly. With that direct-compiled call there is no opportunity for Mockito to substitute its own answers for stubbing or call-tracking logic for verification.

Try mocking readInternal instead, or refactor your code to rely on an interface instead of an implementation. Mockito can mock any method on an interface, because there are no finality or visibility problems allowed within interfaces.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top