What's the point of verifying the times of a function is called with mockito?

  • A+

In my understanding, code testing is to test whether results are right, like a calculator, I need to write a test case to verify if the result of 1+1 is 2.

But I have read many test case about verifying the times of a method called, I'm very confused about that. The best example is what I just saw in Spring in action:

public class BraveKnight implements Knight {     private Quest quest;     public BraveKnight(Quest quest) {          this.quest = quest;      }     public void embarkOnQuest() {         quest.embark();      } }  public class BraveKnightTest {     @Test      public void knightShouldEmbarkOnQuest() {          Quest mockQuest = mock(Quest.class);          BraveKnight knight = new BraveKnight(mockQuest);          knight.embarkOnQuest();          verify(mockQuest, times(1)).embark();      } } 

I really have no idea about why they need to verify the embark() function is called one time. Don't you think that embark() will certainly be invoked after embarkOnQuest() called? Or some errors will occur, and I will be noticed error messages by logs, which show the error line number, that can help me quickly locate the wrong code.

So what's the meaning of verifying like above?


Good question. You raise a good point that mocking can be overly circuitous when you can just check the results. However, there are contexts where this does lead to more robust tests.

For example, if a method needs to make a call to an external API, there are several problems with simply testing the result:

  • Network I/O is slow. If you have many checks like this, it will slow down your test case
  • Any round-trip like this would have to rely on the code making the request, the API, and the code interpreting the API's response all to work correctly. This is a lot of failure points for a single test.
  • If something stupid happens and you accidentally make multiple requests, this could cause performance issues with your program.

To address your sub-questions:

Don't you think that embark() will certainly be invoked after embarkOnQuest() called?

Tests also have value in letting you refactor without worry about breaking things. This is obvious now, yes. Will it be obvious in 6 months?


:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen: