我想测试 Key-Value-Observation 是否适用于我的一个类(class)。它有一个属性,而这个属性又依赖于另一个。它们的设置如下:
+ (NSSet *)keyPathsForValuesAffectingSecondProperty {
return [NSSet setWithObjects:
@"firstProperty",
nil];
}
- (NSArray *)secondProperty {
return [self.firstProperty array];
}
我想运行单元测试以验证当 firstProperty
更改时,绑定(bind)到 secondProperty
的对象会收到通知。起初我以为我可以使用+[OCMockObject observerMock]
,但看起来只能与NSNotificationCenter
一起使用。对此进行测试的最佳方法是什么?
最佳答案
在@chrispix 的回答启发我朝着不同的方向努力之后,我为此工作了一段时间。我从这个开始:
id objectToObserve = [[TheClassBeingTested alloc] init];
id secondPropertyObserver = [OCMockObject mockForClass:[NSObject class]];
[[secondPropertyObserver expect] observeValueForKeyPath:@"secondProperty"
ofObject:objectToObserve
change:OCMOCK_ANY
context:[OCMArg anyPointer]];
[objectToObserve addObserver:secondPropertyObserver
forKeyPath:@"secondProperty"
options:NSKeyValueObservingOptionNew
context:NULL];
// Do something to modify objectToObserve's firstProperty
[secondPropertyObserver verify];
当我运行这段测试代码时,我收到以下消息:
OCMockObject[NSObject]: unexpected method invoked: isKindOfClass:<??>
expected: observeValueForKeyPath:@"firstProperty" ofObject:
我做了一些调查,发现 -isKindOfClass:
调用 mock 对象没想到被传递给 NSKeyValueObservance
类对象。
我尝试添加以下代码来模拟响应,但是 YES
和 NO
的值都因 EXC_BAD_ACCESS
异常而失败,其中 NSKeyValueWillChange堆栈。
BOOL returnVal = NO;
[[[secondPropertyObserver stub] andReturnValue:OCMOCK_VALUE(returnVal)] isKindOfClass:[OCMArg any]];
我更加小心地发现我的代码并没有导致这个异常——它是在 autoreleasepool
被耗尽时引起的。然后我突然意识到我需要移除观察者。下面是完整的解决方案,包括移除观察者。
id objectToObserve = [[TheClassBeingTested alloc] init];
id secondPropertyObserver = [OCMockObject mockForClass:[NSObject class]];
BOOL returnVal = NO;
[[[secondPropertyObserver stub] andReturnValue:OCMOCK_VALUE(returnVal)] isKindOfClass:[OCMArg any]];
[[secondPropertyObserver expect] observeValueForKeyPath:@"secondProperty"
ofObject:objectToObserve
change:OCMOCK_ANY
context:[OCMArg anyPointer]];
[objectToObserve addObserver:secondPropertyObserver
forKeyPath:@"secondProperty"
options:NSKeyValueObservingOptionNew
context:NULL];
// Do something to modify objectToObserve's firstProperty
[secondPropertyObserver verify];
[objectToObserve removeObserver:secondPropertyObserver
forKeyPath:@"secondProperty"];
关于objective-c - 使用 OCMock 模拟 KVO,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9603362/