I've been attempting to write some fail fast tests using OCMReject. However I've found that if OCMStub is used in conjunction with OCMReject, this test will pass
id _mockModel = OCMProtocolMock( @protocol( CTPrefModelProtocol));
//It doesn't seem to matter what order these two are in, the test behaves the same
OCMStub([_mockModel getPreferences]);
OCMReject([_mockModel getPreferences]);
[_mockModel getPreferences];
Even though it should clearly fail because I'm calling the function that I've set in the OCMReject method.
I realise I can just stub getPreferences whenever I'm expecting a result from it and remove it from this test, but largely that means if I've set a stub on getPreferences in my setUp method, any test that calls OCMReject([_mockModel getPreferences])
will just be ignored.
Why am I not able to use OCMStub and OCMReject together? Is it because OCMStub alters getPreferences somehow and as a result whenever I call this method, it actually calls some other method instead?
So apparently I can't read. Reading through the OCMock 3 Documentation, under the limitations heading 10.2
Setting up expect after stub on the same method does not work
id mock = OCMStrictClassMock([SomeClass class]);
OCMStub([mock someMethod]).andReturn(@"a string");
OCMExpect([mock someMethod]);
/* run code under test */
OCMVerifyAll(mock); // will complain that someMethod has not been called
The code above first sets up a stub for someMethod and afterwards an expectation for the same method. Due to the way mock objects are currently implemented any calls to someMethod are handled by the stub. This means that even if the method is called the verify fails. It is possible to avoid this problem by adding andReturn to the expect statement. You can also set up a stub after the expect.
I suspect this same limitation exists for OCMReject as well. Hopefully this helps equally blind people like myself. A link to the documentation for the lazy.