Expect-run-verify is the most common pattern in mock frameworks. (update: I called it record-replay-verify before – my bad – expect-run-verify is what I really meant).
What’s wrong with it?
- Codebase suffers. Test methods become noisy. I have to expect/record some interactions not because I want to test them but because mocks complain if I don’t do it.
- Doesn’t give me a natural test-drive. I prefer when expectations become assertions and appear after execution – it’s very intuitive.
- Tests are fragile. Test driving new functionality that requires additional interaction often breaks all tests. Thanks to the aggressive nature of expect-run-verify.
- Could give better failures. When expectation becomes assertion, failure shows exact line of code. No more deciphering exception messages – just click on first element on stack trace.
- Could read better. Separation of stubbing and expectations reads really nicely.
MoQ uses C# 3.0 sugar like lambda expressions. Mockito is a java creature. Both don’t like record/playback model. Mockito goes even further and abandons expect-run-verify.
Let me enjoy most natural test-drive: as close to state based testing as possible. Expectations in Mockito are like assertions – good old friends of state based testing.
Java TDDer have several options these days:
- Using hand crafted stubs/mocks: too much boilerplate, too many lines of code, chaos of stubs.
- Using existing mock libraries: less some obscure exceptions it’s all expect-run-verify stuff.
- Mockito: just try it and tell me what you don’t like about it :)
I know that many test-infected java people on this planet don’t use mock frameworks. They code mocks/stubs from scratch because they find mock libraries too annoying. Mockito offers simplicity and flexibility of hand crafted mocks and yet eliminates so much boilerplate code. I encourage you to try it out.