Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Mockito: multiple calls to the same method

I am mocking an object with Mockito, the same method on this object is called multiple times and I want to return the same value every time.
This is what I have:

LogEntry entry = null; // this is a field
// This method is called once only.
when(mockLogger.createNewLogEntry()).thenAnswer(new Answer<LogEntry>() {
  @Override
  public LogEntry answer(InvocationOnMock invocationOnMock) throws Throwable {
    entry = new LogEntry();
    return entry;
  }
});
// This method can be called multiple times, 
// If called after createNewLogEntry() - should return initialized entry.
// If called before createNewLogEntry() - should return null.
when(mockLogger.getLogEntry()).thenAnswer(new Answer<LogEntry>() {
  @Override
  public LogEntry answer(InvocationOnMock invocationOnMock) throws Throwable {
    return entry;
  }
});

The problem is, it seems that my getLogEntry method is called only once. For all subsequent invocations, null is returned instead and I get NPEs in tests.
How can I tell mockito to use stubbed version for all calls?

=================================================================
Post mortem for future generations

I did some additional investigation and as always it is not library's fault, it is my fault. In my code one of the methods called getLogEntry() before calling createNewLogEntry(). NPE was absolutely legitimate, the test actually found a bug in my code, not me finding bug in Mockito.

like image 676
Ula Krukar Avatar asked Nov 20 '12 14:11

Ula Krukar


2 Answers

Your stub should work as you want it. From Mockito doc:

Once stubbed, the method will always return stubbed value regardless of how many times it is called.

like image 154
ShyJ Avatar answered Oct 04 '22 20:10

ShyJ


Unless I'm missing something, if you want to return the same object for each method invocation then why not simple do:

final LogEntry entry = new LogEntry()
when(mockLogger.createNewLogEntry()).thenReturn(entry);
when(mockLogger.getLogEntry()).thenReturn(entry);

...

verify(mockLogger).createNewLogEntry();
verify(mockLogger, times(???)).getLogEntry();

Mockito will return the same value for every matching call.

like image 39
Jonathan Avatar answered Oct 04 '22 20:10

Jonathan