简体   繁体   中英

Mock kafka producer in jUnit to test Future(Java)

I am changing the implementation of how kafka sends events from async to sync

I found the following

 producer.send(producerRecord, (m, e) -> {
    ...some login...
 }).get();
 } catch (InterruptedException | RuntimeException | ExecutionException e) {
       logger.info("", e);
       throw new RuntimeException(e);
 }

I've added the get() method, which makes the code wait for a response before moving to the next one.

I now want to create a jUnit test to test this but I'm struggling to do so I'm mocking the producer using Mockito Then I'm using the following code

KafkaProducer mockProducer = Mockito.mock(KafkaProducer.class);
Future<RecordMetadata> future = Mockito.mock(Future.class);
doReturn(future).when(mockProducer).send(any());
when(future.get()).thenThrow(InterruptedException.class);
communicator.sendEvent(eventValue);//sendEvent then calls the producer and sends an event

I'm getting NullPointerException for some reason but when I evaluate producer.sendEvent and also producer.sendEvent(producerRecord).get() in the debugger. They both have values

So I'm not sure what's wrong.

any advice will be appreciated

You do not mock the method that you call later (as @kiuby_88 already mentioned in a comment).

So you should do it in your test like this:

KafkaProducer mockProducer = Mockito.mock(KafkaProducer.class);
Future<RecordMetadata> future = Mockito.mock(Future.class);

when(mockProducer).send(any(), any()).thenReturn(future);
when(future.get()).thenThrow(InterruptedException.class);

communicator.sendEvent(eventValue);

You mixed the doReturn style of Mockito configurations with the when style, which is confusing a bit. The doReturn style was introduced for setting up reactions on the call of methods returning void but can also be used to return values from other methods - but in my opinion it reduces confusion of the reader of you test-code, if you use one style throughout a whole test. An alternative style would be:

doReturn(future).when(mockProducer).send(any(), any());
doThrow(InterruptedException.class).when(future).get();

See also the docs of Mockito about the doReturn()|doThrow()|doAnswer()|doNothing()|doCallRealMethod() family of methods

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM