Giới thiệu Framework OCMock
Bài đăng này đã không được cập nhật trong 3 năm
1. Giới thiệu
Nếu search key word 'mock object' trên github bạn sẽ nhận được 1 list các thư viện, và khi chọn mục objective C bạn sẽ thấy thư viện OCMock đầu tiên với hơn 1000 sao. Trong bài viết này tôi sẽ giới thiệu với các bạn thư viện OCMock dùng để viết Mock cho iOS.
2. Yêu cầu
-
Có kiến thức sơ lược về test double, test stub, test spy, Mocking Object Tham khảo tại:
https://en.wikipedia.org/wiki/Test_double http://xunitpatterns.com/Test Double.html
3. Cài đặt
-
Download phiên bản mới nhất tại
-
Giải nén được file libOCMock.a và thư mục chứa file header OCMock.
-
Tạo Thư mục như sau và copy vào folder project
-
Add library libOCMock.a
-
Config target Project Test như sau
-
Ở mục header search path add: '$(PROJECT_DIR)/usr/include'
-
Ở mục library search path add: '$(PROJECT_DIR)/usr/lib'
-
4. Practice
Tình huống đặt ra là tôi có một list các persons hiển thị lên table view. Tôi có một phím add button khi nhấn vào phím thì add thêm một person vào datasource và reload lại tableview. Tôi muốn test là khi hàm add được gọi thì tableView được reload lại.
-
Hàm
addPerson
của controller:- (IBAction)addPerson:(id)sender { Person *person = [Person new]; person.idNumber = (int)self.persons.count; person.name = @"Test"; person.age = random()%20; [self.personDAO addPerson:person]; self.persons = [self.personDAO loadPersons]; [self.tableView reloadData]; }
-
Hàm Test của hàm add:
- (void)testAdd{ //Stub id plistMock = OCMClassMock([PListPersonDAO class]); self.vc.personDAO = plistMock; [self.vc addPerson:nil]; //Test Spy OCMVerify([plistMock loadPersons]); }
Ở đoạn code trên tôi sử dụng OCMClassMock
để tạo stub bạn có thể add thêm các behavior cho stub
sử dụng các hàm dưới đây:
- (id)andReturn:(id)anObject;
- (id)andReturnValue:(NSValue *)aValue;
- (id)andThrow:(NSException *)anException;
- (id)andPost:(NSNotification *)aNotification;
- (id)andCall:(SEL)selector onObject:(id)anObject;
- (id)andDo:(void (^)(NSInvocation *invocation))block;
- (id)andForwardToRealObject;
Và cuối cùng tôi sử dụng OCMVerify
để verify rằng hàm loadPersons
của pListDAO
được gọi.
7. Các tính năng khác
-
Class mocks:
id mock = [OCMockObject mockForClass:[SomeClass class]]
-
Expectations and verification:
-
Setup Verfiied Parameter
[[mock expect] someMethod:someArgument]
-
Verify:
[mock verify]
-
Delay verify:
[mock verifyWithDelay:aDelay]
-
-
Stubs:
-
Add and return value:
[[[mock stub] andReturn:aValue] someMethod:someArgument]
-
Add Method and throw exception:
[[[mock stub] andThrow:anException] someMethod:someArgument]
-
Add Method with expected block:
void (^theBlock)(NSInvocation *) = ^(NSInvocation *invocation) {}; [[[mock stub] andDo:theBlock] someMethod:[OCMArg any]];
-
-
Class Methods:
[[[mock stub] andReturn:aValue] someClassMethod]
-
Argument Constraint:
[[mock expect] someMethod:[OCMArg any]] [[mock expect] someMethod:[OCMArg isNotNil]] [[mock expect] someMethod:[OCMArg isNotEqual:aValue]]
-
Protocol mocks: Create object conform to protocol
id aMock = [OCMockObject mockForProtocol:@protocol(SomeProtocol)]
-
Observer mocks:
-
Create observer mock:
id aMock = [OCMockObject observerMock]
-
Assgin notification observer to mock:
[notificatonCenter addMockObserver:aMock name:SomeNotification object:nil]
-
6. Kết luận
- So với thư viện Mockito của java thì thư viện OCMock còn thiếu nhiều Utility nhưng chúng rất có lợi cho việc test các hàm và behavior của app.
- Tham khảo thêm tại: http://ocmock.org/reference/
- Link Code: http://www.mediafire.com/download/7i9z5h9chv5jvps/OCMockTest.zip
All rights reserved