我已经开始与OCMock合作为我已经集成到项目工作区的现有项目编写测试用例.完成此链接中提到的所有步骤后
当我第一次执行我的测试用例时,它给了我这个错误.我搜索了它并尝试了一些解决方案,如"创建新目标","重新启动Xcode",但它没有帮助我.任何的想法?
我经常在我的iPhone Objective-C单元测试中发现我想要一个类方法,例如NSUrlConnection的+ sendSynchronousRequest:returningResponse:error:方法.
简化示例:
- (void)testClassMock
{
id mock = [OCMockObject mockForClass:[NSURLConnection class]];
[[[mock stub] andReturn:nil] sendSynchronousRequest:nil returningResponse:nil error:nil];
}
Run Code Online (Sandbox Code Playgroud)
运行时,我得到:
Test Case '-[WorklistTest testClassMock]' started.
Unknown.m:0: error: -[WorklistTest testClassMock] : *** -[NSProxy doesNotRecognizeSelector:sendSynchronousRequest:returningResponse:error:] called!
Test Case '-[WorklistTest testClassMock]' failed (0.000 seconds).
Run Code Online (Sandbox Code Playgroud)
我很难找到关于此的任何文档,但我认为OCMock不支持类方法.
经过很多谷歌搜索,我发现了这个提示.它有效,但非常麻烦:http: //thom.org.uk/2009/05/09/mocking-class-methods-in-objective-c/
无论如何在OCMock中这样做?或者有人会想到一个聪明的OCMock类别对象可以编写来完成这种事情吗?
在我的日常工作中,我被Mockito的never()验证所破坏,这可以确认一个模拟方法永远不会被调用.
有没有办法用Objective-C和OCMock完成同样的事情?我一直在使用下面的代码,它可以工作,但感觉就像一个黑客.我希望有更好的方法......
- (void)testSomeMethodIsNeverCalled {
id mock = [OCMockObject mockForClass:[MyObject class]];
[[[mock stub] andCall:@selector(fail) onObject:self] forbiddenMethod];
// more test things here, which hopefully
// never call [mock forbiddenMethod]...
}
- (void)fail {
STFail(@"This method is forbidden!");
}
Run Code Online (Sandbox Code Playgroud) 我正在学习如何使用OCMock来测试我的iPhone项目,我有这样的场景:带有getHeightAtX:andY:方法的HeightMap类和使用的Render类HeightMap.我正在尝试使用一些HeightMap模拟单元测试渲染.这有效:
id mock = [OCMockObject mockForClass:[Chunk class]];
int h = 0;
[[[mock stub] andReturnValue:OCMOCK_VALUE(h)] getHeightAtX:0 andY:0];
Run Code Online (Sandbox Code Playgroud)
当然,仅适用于x=0和y=0.我想测试使用"平面"高度图.这意味着我需要做这样的事情:
id chunk = [OCMockObject mockForClass:[Chunk class]];
int h = 0;
[[[chunk stub] andReturnValue:OCMOCK_VALUE(h)] getHeightAtX:[OCMArg any] andY:[OCMArg any]];
Run Code Online (Sandbox Code Playgroud)
但这引发了两个编译警告:
警告:
'getHeightAtX:andY:'从没有强制转换的指针传递整数的参数1
和运行时错误:
调用了意外的方法:
'getHeightAtX:0 andY:0 stubbed: getHeightAtX:15545040 andY:15545024'
我错过了什么?我发现无法传递anyValue给这个模拟器.
我正在使用OCMock 1.70,并且在模拟返回BOOL值的简单方法时出现问题.这是我的代码:
@interface MyClass : NSObject
- (void)methodWithArg:(id)arg;
- (BOOL)methodWithBOOLResult;
@end
@implementation MyClass
- (void)methodWithArg:(id)arg {
NSLog(@"methodWithArg: %@", arg);
}
- (BOOL)methodWithBOOLResult {
NSLog(@"methodWithBOOLResult");
return YES;
}
@end
- (void)testMock {
id real = [[[MyClass alloc] init] autorelease];
[real methodWithArg:@"foo"];
//=> SUCCESS: logs "methodWithArg: foo"
id mock = [OCMockObject mockForClass:[MyClass class]];
[[mock stub] methodWithArg:[OCMArg any]];
[mock methodWithArg:@"foo"];
//=> SUCCESS: "nothing" happens
NSAssert([real methodWithBOOLResult], nil);
//=> SUCCESS: logs "methodWithBOOLResult", YES returned
BOOL boolResult = YES;
[[[mock stub] andReturn:OCMOCK_VALUE(boolResult)] methodWithBOOLResult];
NSAssert([mock methodWithBOOLResult], …Run Code Online (Sandbox Code Playgroud) 假设方法签名如下:
- (void)theMethod:(void(^)(BOOL completed))completionBlock;
Run Code Online (Sandbox Code Playgroud)
我想模拟这个方法签名,以确保调用该方法,并只调用完成块.我从其他的帖子好像看到这一个,我可以嘲笑的方法调用,并接受任何块,但是不会运行块.我也知道有一种我可以使用的doDo方法,但我无法弄清楚如何传递一个块并运行它.
有任何想法吗?
谢谢.
看来我第一次在OCMock存根上添加andReturnValue时,返回值就是一成不变的.例如:
id physics = [OCMockObject niceMockForClass:[DynamicPhysicsComponent class]
Entity *testEntity = [Entity entityWithPhysicsComponent:physics];
CGPoint velocity1 = CGPointMake(100, 100);
CGPoint velocity2 = CGPointZero;
[[[physics stub] andReturnValue:OCMOCK_VALUE(velocity1)] getCurrentVelocity];
[testEntity update:0.1];
[[[physics stub] andReturnValue:OCMOCK_VALUE(velocity2)] getCurrentVelocity];
[testEntity update:0.1];
Run Code Online (Sandbox Code Playgroud)
在[testEntity update]中调用stubbed方法.但每次stubbed方法返回velocity1值,所以我猜第二次尝试设置方法的返回值是不值得的.
有没有办法在OCMock中做到这一点?
我正在编写一个需要从Web服务器获取一些数据的iPhone应用程序.我正在使用NSURLConnectionHTTP请求,这很有效,但在响应有HTTP错误代码(如404或500)的情况下,我无法对代码进行单元测试.
当服务器返回一个错误,该连接不会调用connection:didFailWithError:的委托,但呼吁connection:didReceiveResponse:,connection:didReceiveData:以及connectionDidFinishLoading:代替.我正在检查响应中的状态代码connection:didReceiveResponse:并cancel在状态代码看起来像一个错误时调用连接以防止connectionDidFinishLoading:被调用,其中将报告成功的响应.
提供静态存根NSURLConnection很简单,但我希望我的测试在调用其中一个模拟连接的方法时改变它的行为.具体来说,我希望测试能够告诉代码何时调用cancel模拟连接,因此测试可以停止调用connection:didReceiveData:和connectionDidFinishLoading:代理.
有没有办法让测试判断是否cancel已经在模拟对象上调用了?有没有更好的方法来测试使用的代码NSURLConnection?有没有更好的方法来处理HTTP错误状态?
我正在尝试模拟一个具有以下签名等效方法:
- (NSDictionary *) uploadValues:(BOOL)doSomething error:(NSError **)error
Run Code Online (Sandbox Code Playgroud)
我希望它返回一个小字典,以便我的测试可以确保代码正确使用字典.但是,无论我做什么,OCMock总是从方法中返回nil,无论我如何将其存根.错误在我正在测试的代码中以nil开头,这些是我尝试将其存根的不同方式:
NSError * error = nil;
[[[mock stub] andReturn:someDict] uploadValues:YES error:&error];
[[[mock stub] andReturn:someDict] uploadValues:YES error:nil];
[[[mock stub] andReturn:someDict] uploadValues:YES error:[OCMArg any]];
Run Code Online (Sandbox Code Playgroud)
并且它们都不起作用.OCMock是否支持处理作为存根消息参数,如果是,那么正确的方法是什么?
ocmock ×10
objective-c ×5
unit-testing ×5
iphone ×3
cocoa ×2
cocoa-touch ×2
ios ×2
mocking ×2
handle ×1
mockito ×1
primitive ×1
xcode ×1
xcode7 ×1