0

我正在使用 Kiwi 为应用程序编写测试。我正在尝试验证从返回的单元格tableView:cellForRowAtIndexPath:在调用后是否设置了正确的值。我已经做了很多不同的变化,但没有运气:

describe(@"tableView:cellForRowAtIndexPath:", ^{

  it(@"Should return a cell with proper label values",
     ^{
       NSIndexPath *indexPath = [NSIndexPath indexPathForRow:0 inSection:0];
       id mockTableView = [UITableView mock];
       id mockCell = [UITableViewCell mock];
       [mockTableView stub:@selector(dequeueReusableCellWithIdentifier:forIndexPath:) andReturn:mockCell withArguments:any(), indexPath];
       [mockCell stub:@selector(label1)
            andReturn:[[UILabel alloc] init]];
       [mockCell stub:@selector(label2)
            andReturn:[UILabel alloc]];

       CustomTableViewCell *cell = (CustomTableViewCell *)
           [dataSource tableView:mockTableView
                   cellForRowAtIndexPath:indexPath];

       [[cell.label1.text should]
           equal:@"abc"];
       [[cell.label2.text should] equal:@"xyz"];

     });

});

实际方法如下所示:

- (UITableViewCell *)tableView:(UITableView *)tableView
         cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
  CustomTableViewCell *cell =
      [tableView dequeueReusableCellWithIdentifier:kCustomCellReuseIdentifier
                                      forIndexPath:indexPath];
  CustomObject *obj = [self objAtIndexPath:indexPath];

  [self setupCell:cell withObj:obj];

  return cell;
}

- (void)setupCell:(
CustomTableViewCell *)cell withObj:(CustomObject *)obj
    {
      cell.label1.text = @"abc";
      cell.label2.text = @"xyz";
    }

它似乎被抓住了cell.label1——nil然而,我之前确实存根存根。

欢迎任何关于如何实际编写此测试的想法。

4

2 回答 2

0

如果您通过情节提要以编程方式实例化 CustomTableViewController,则如果将自定义单元格连接为插座,则无需在自定义单元格上设置标签。但是,看起来您可能正在以编程方式构建单元 UI,因此只需在运行测试操作之前像这样初始化模拟的 CustomCell 上的标签:

describe(@"CustomTableViewControllerTest", ^{
    __block CustomTableViewController *controller;

    beforeEach(^{
        controller = [[CustomTableViewController alloc] initWithStyle:UITableViewStylePlain];
        controller.tableView = [[UITableView alloc] init];
    });

    describe(@"tableView:cellForRowAtIndexPath:", ^{
        it(@"Should return a cell with proper label values", ^{
            NSIndexPath *indexPath = [NSIndexPath indexPathForRow:0 inSection:0];
            CustomTableViewCell *mockCell = [[CustomTableViewCell alloc] init];
            mockCell.label1 = [[UILabel alloc] init];
            mockCell.label2 = [[UILabel alloc] init];
            [controller.tableView stub:@selector(dequeueReusableCellWithIdentifier:forIndexPath:) andReturn:mockCell withArguments:any(), indexPath];
            CustomTableViewCell *cell = (CustomTableViewCell *)[controller tableView:controller.tableView cellForRowAtIndexPath:indexPath];
            [[cell.label1.text should] equal:@"abc"];
            [[cell.label2.text should] equal:@"xyz"];
        });
    });
});

请记住,并非所有事情都需要模拟。事实上,我相信在编写测试时尽可能少地模拟会更好,因为它可以让你的对象在创建后负责正确的行为。我在本地运行它,它通过了。

于 2015-05-18T01:10:48.983 回答
0

当你在测试 UIKit 类时,你是否看到过 Kiwi wiki 页面,上面写着以下内容?

对 UIKit 类(例如 UILabels)执行操作的规范如果在应用程序测试以外的任何东西下运行,它们可能会奇怪地崩溃。要了解有关如何设置应用程序测试目标的更多信息,请查看Apple 官方文档

听起来您可能想确保测试目标是应用程序测试,而不是逻辑测试。

于 2015-07-01T18:42:22.000 回答