OCUnit 测试 Objective-C 中的协议/回调/委托 [英] OCUnit test for protocols/callbacks/delegate in Objective-C

查看:22
本文介绍了OCUnit 测试 Objective-C 中的协议/回调/委托的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

使用 OCUnit,有没有办法测试委托协议?

Using OCUnit, is there a way to test delegate protocols?

我正在尝试这个,它不起作用.

I'm trying this, which doesn't work.

-(void) testSomeObjDelegate {
  SomeObj obj = [[SomeObj alloc] initWithDelegate:self];
  [obj executeMethod];
}
-(void) someObjDelegateMethod {
  //test something here
}

我将尝试在另一个线程上调用 obj 方法并让测试休眠,直到调用委托.似乎应该有一种更简单的方法来测试它.

I'm going to try calling the obj method on a different thread and have the test sleep until the delegate is called. It just seems like there should be an easier way to test this.

推荐答案

测试委托很简单.只需在回调方法的测试中设置一个 ivar,并在应该触发委托回调后检查它.

Testing a delegate is trivial. Just set an ivar in the test in your callback method, and check it after what should be triggering the delegate callback.

例如,如果我有一个类 Something 使用协议 SomethingDelegate 的委托并将该委托 -something:delegateInvoked: 发送到响应一些消息,我可以像这样测试它:

For example, if I have a class Something that uses a delegate of protocol SomethingDelegate and sends that delegate -something:delegateInvoked: in response to some message, I can test it lik ethis:

@interface TestSomeBehavior : SenTestCase <SomethingDelegate>
{
    Something *_object;
    BOOL _callbackInvoked;
}
@end

@implementation TestSomeBehavior

- (void)setUp {
    [super setUp];
    _object = [[Something alloc] init];
    _object.delegate = self;
}

- (void)tearDown {
    _object.delegate = nil;
    [_object release];
    [super tearDown];
}

- (void)testSomeBehaviorCallingBack {
    [_object doSomethingThatShouldCallBack];

    STAssertTrue(_callbackInvoked,
                 @"Delegate should send -something:delegateInvoked:");
}

- (void)something:(Something *)something delegateInvoked:(BOOL)invoked {
    _callbackInvoked = YES;
}

@end

但是,我认为您已经从您提出问题的方式中理解了这一点.(我主要是为其他读者发布此内容.)我认为您实际上是在问一个更微妙的问题:我如何测试可能稍后发生的东西,例如旋转运行循环的东西.我的暗示是你提到的睡眠和穿线.

I think you already understand this, however, from the way you've phrased your question. (I'm mostly posting this for other readers.) I think you're actually asking a more subtle question: How do I test something that may occur later such as something that spins the runloop. My cue is your mention of sleeping and threading.

首先,您不应该随意调用另一个线程上的方法.只有当它被记录为可以安全使用时,您才应该这样做.原因是你不知道类的内部是做什么的.例如,它可能会在运行循环上安排事件,在这种情况下,在不同的线程上运行该方法将使它们发生在不同的运行循环上.这会搞砸类的内部状态.

First off, you should not just arbitrarily invoke a method on another thread. You should only do so if it's documented to be safe to use in that way. The reason is that you don't know what the internals of the class do. For example, it might schedule events on the run loop, in which case running the method on a different thread will make them happen on a different run loop. This would then screw up the class's internal state.

如果您确实需要测试一些可能需要一些时间才能发生的事情,您可以通过运行当前的运行循环来做到这一点.以下是我可能会如何重写上面的单个测试方法来做到这一点:

If you do need to test something that may take a little time to happen, you can do this just by running the current run loop. Here's how I might rewrite the individual test method above to do that:

- (void)testSomeBehaviorCallingBack {
    NSDate *fiveSecondsFromNow = [NSDate dateWithTimeIntervalSinceNow:5.0];

    [_object doSomethingThatShouldCallBack];

    [[NSRunLoop currentRunLoop] runUntilDate:fiveSecondsFromNow];

    STAssertTrue(_callbackInvoked,
                 @"Delegate should send -something:delegateInvoked:");
}

这将使当前运行循环在默认模式下旋转 5 秒,假设 -doSomethingThatShouldCallBack 将在默认模式下将其工作安排在主运行循环上.这通常没问题,因为以这种方式工作的 API 通常允许您指定要使用的运行循环以及要运行的模式.如果可以这样做,那么您可以使用 -[NSRunLoop runMode:beforeDate:] 以仅在该模式下运行运行循环,从而更有可能完成您期望完成的工作.

This will spin the current run loop in the default mode for 5 seconds, under the assumption that -doSomethingThatShouldCallBack will schedule its work on the main run loop in the default mode. This is usually OK because APIs that work this way often let you specify a run loop to use as well as a mode to run in. If you can do that, then you can use -[NSRunLoop runMode:beforeDate:] to run the run loop in just that mode instead, making it more likely that the work you're expecting to be done will be.

这篇关于OCUnit 测试 Objective-C 中的协议/回调/委托的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆