Open-source project
jonreid/OCMockito avatar
jonreid/OCMockito

OCMockito keeps every mock nice and drops the expect-run-verify ritual

Mockito for Objective-C: creation, verification and stubbing of mock objects

987 stars119 forksObjective-CMIT

At a glance

What is it?
OCMockito is an Objective-C implementation of Mockito, and its three stated differences from other mocking frameworks are the whole design: mocks are always nice and record calls instead of complaining about unspecified invocations, there is no expect-run-verify phase, and verification failures come back as unit test failures that point at a line rather than as thrown exceptions. It ships through CocoaPods, Carthage, Swift Package Manager and a prebuilt framework.
Who is it for?
OCMockito fits a team with an existing Objective-C or mixed Swift and Objective-C test suite that wants Mockito's readability without the ceremony, and the always nice behaviour is what stops a new test from failing because a mock method nobody stubbed happened to be called.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 142 days ago.
What is it written in?
Mainly Objective-C, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on November 7, 2026, and from our analysis. They are not legal advice.

From daily snapshots

Star history

  • jonreid/OCMockito987 ★ · +0
Star history
Repository2026-10-212026-11-07
jonreid/OCMockito987987

0 Stars in the last 17 days, measured from the daily GitHub snapshot. Compare with other projects

Editorial analysis

Three differences from other mocking frameworks

The README lists the key differences from other mocking frameworks, and they are specific enough to describe the library in a paragraph. First, mock objects are always nice, recording their calls instead of throwing exceptions about unspecified invocations, and the stated benefit is that this makes tests less fragile. Second, there is no expect-run-verify, which makes tests more readable, because mock objects record their calls and then you verify the methods you want. Third, verification failures are reported as unit test failures that identify specific lines instead of throwing exceptions, which makes it easier to identify where a failure happened. Each of those three is a deliberate trade-off against other mocking styles. Strict mocks, for instance, turn unstubbed calls into errors, which catches bugs but also makes tests brittle in ways unrelated to what is being tested. The expect phase is a lot of structure to carry for every test. And an exception thrown deep inside a framework call site, with the real failure several frames away, is harder to read than a failed assertion on a specific line.

Record first, verify afterwards

The verification workflow is short enough to show in full. You create a mock of a class, use it, and then verify the calls you care about:

obj-c
// mock creation
NSMutableArray *mockArray = mock([NSMutableArray class]);

// using mock object
[mockArray addObject:@"one"];
[mockArray removeAllObjects];

// verification
[verify(mockArray) addObject:@"one"];
[verify(mockArray) removeAllObjects];

Once created, the mock remembers all interactions, and you can then selectively verify whatever interactions you are interested in. There is a practical detail here that trips people up the first time, and the README calls it out: if Xcode complains about multiple methods with the same name, cast verify to the mocked class. The verify macro expands to an expression that has to be typed against the object, and the compiler sometimes resolves the wrong overload when a class has several methods that share a name. Casting it to the mocked class is the documented way to settle that ambiguity.

Stubbing, and the unstubbed default

Stubbing uses a given wrapper around the call you want to control:

obj-c
// mock creation
NSArray *mockArray = mock([NSArray class]);

// stubbing
[given([mockArray objectAtIndex:0]) willReturn:@"first"];

The behaviour of an unstubbed call is the interesting part, because it follows from the always nice rule. The README shows that a call to objectAtIndex:999, which was never stubbed, prints (null), while the stubbed index 0 prints first and the stubbed index 1 throws the exception you configured. So an unstubbed object returning method gives you nil, quietly, and only the calls you have explicitly configured misbehave. That is the trade you accept in exchange for the fragility argument in the first section, and it means a mock will not catch a call your production code makes but your test did not anticipate. A test that asserts the specific interactions you care about with verify is what compensates for it.

Classes, protocols and objects that are both

OCMockito covers the three creation cases an Objective-C codebase runs into. A class object is mocked with mockClass, and the README notes the runtime caveat that on the iOS 64-bit runtime Class objects are not strong by default, so you either make it explicitly strong or use id instead:

obj-c
__strong Class mockStringClass = mockClass([NSString class]);

A protocol is mocked with mockProtocol, and if you do not want the mock to respond to any optional methods of that protocol there is a separate constructor for it:

obj-c
id <MyDelegate> delegate = mockProtocol(@protocol(MyDelegate));

The third case is an object that is both a class and a protocol implementer, which is common for view controllers that adopt a delegate protocol, and it has its own constructor taking the class and the protocol. There is a section in the README on mocking a singleton, and a separate section on problems with dealloc, which are the two places where a runtime-swizzling based mock is genuinely awkward rather than merely inconvenient.

Primitives, structs and KVO properties

The return type of the method you are stubbing determines how you express the value, and the README covers each case. A method returning a primitive scalar is stubbed by boxing the scalar into an NSValue, so a count is stubbed with willReturn:@3. A method returning a struct is stubbed with willReturnStruct:objCType:, taking a pointer to the structure and its type from the Objective-C @encode() compiler directive, which is how the library knows how to copy the bytes. A property that needs to work with key value observing is a third case, and it has its own helper, stubProperty, which stubs the property along with valueForKey: and valueForKeyPath: so that observation still fires:

obj-c
stubProperty(mockEmployee, firstName, @"FIRST-NAME");

That last one is the detail that matters in a UI test suite, because KVO is how most Objective-C view code reacts to model changes, and a mock that returns a value without firing the observer will pass a unit test and fail in the running app. The README also covers capturing arguments for further assertions and stubbing consecutive calls, which are the two features that show up once a test needs to assert on the arguments a method was called with.

Argument matchers come from OCHamcrest

By default OCMockito verifies argument values by testing for equality, and when more flexibility is needed the README points you at OCHamcrest matchers, which are specified as arguments for both verification and stubbing:

obj-c
// mock creation
NSMutableArray *mockArray = mock([NSMutableArray class]);

// using mock object
[mockArray removeObject:@"This is a test"];

// verification
[verify(mockArray) removeObject:startsWith(@"This is")];

One warning is documented: a typed argument will issue a warning that the matcher is the wrong type, and the fix is to cast the matcher to id. For a method that takes a non-object argument and you still want to match it, the technique is to invoke the method with a dummy argument and then call -withMatcher:forArgument:, as in:

obj-c
[[given([mockArray objectAtIndex:0]) withMatcher:anything() forArgument:0]
 willReturn:@"foo"];

This is a two step call rather than a single expression, which reads a little awkwardly in a test, but it keeps the matcher tied to a specific argument position, which matters when a method takes more than one.

Four ways to install it, and a release gap

The installation section covers Swift Package Manager, CocoaPods, Carthage, a prebuilt framework and building it yourself, which is generous coverage for a library that has been around long enough to accumulate every packaging option. The repository reflects that history in its layout, with an OCMockito.podspec for CocoaPods, a Cartfile and Cartfile.project for Carthage, a Package.swift for Swift Package Manager, an OCMockito.xcodeproj directory, a Frameworks directory for the prebuilt option, and a Sources directory for the code itself. There are example projects per packaging method, for macOS and for iOS, covering CocoaPods, the framework and Swift Package Manager separately. The licence is MIT and the project integrates with XCTest, with the GitHub Actions build workflow and the Coveralls coverage badge visible at the top. The release history is the part to look at carefully, because the newest tagged versions are v7.0.2 from 2023-10-02, v7.0.1 from 2022-03-14 and v7.0.0 from 2021-11-25, while the last push to the repository was on 2026-06-19. The work continues, but the tags have not moved in a long time.

Editorial conclusion

OCMockito fits a team with an existing Objective-C or mixed Swift and Objective-C test suite that wants Mockito's readability without the ceremony, and the always nice behaviour is what stops a new test from failing because a mock method nobody stubbed happened to be called. It does not fit a Swift-only project, since the library is Objective-C, and it does not fit a team that needs a current release, because the newest tagged version is v7.0.2 from 2023-10-02 even though the last push was on 2026-06-19, so you are depending on a source tree rather than a release. Before you add it, check the installation path you intend to use, since the repository documents five installation paths, read the section on dealloc and singleton mocking before you design a test around either, and pin the commit you build from.

Frequently asked questions

What is OCMockito?

It is an Objective-C implementation of Mockito supporting creation, verification and stubbing of mock objects, with always nice mocks that record calls, no expect-run-verify phase, and verification failures reported as unit test failures pointing at specific lines.

What happens when I call a method on a mock that I did not stub?

Because mocks are always nice, the call is recorded and the default return value is used, so an unstubbed object returning method gives you nil rather than an exception. Only the calls you explicitly stub behave differently, for example returning a value or throwing.

How do I mock a protocol or a class object in OCMockito?

Use mockProtocol with the protocol, or mockProtocolWithoutOptionals to leave out the optional methods, and mockClass for a class object. On the iOS 64-bit runtime a class mock must be declared __strong or you use id instead.

How do I stub a method that returns a primitive or a struct?

Primitives are boxed into NSValues, so a count is stubbed with willReturn:@3. Structs are stubbed with willReturnStruct:objCType:, passing a pointer to the struct and its type from the @encode() compiler directive.

Is OCMockito still maintained?

The repository is not archived and the last push was on 2026-06-19, but the newest tagged release is v7.0.2 from 2023-10-02, so there is no recent version to depend on.

Official sources

  1. Issues
  2. jonreid/OCMockito on GitHub
  3. License: MIT
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/jonreid-ocmockito.svg)](https://hysenlabs.com/projects/jonreid-ocmockito)

Star history chart for your README

markdown
[![Star history](https://hysenlabs.com/chart/jonreid-ocmockito.svg)](https://hysenlabs.com/projects/jonreid-ocmockito)

Was this useful?