如何运行和调试iPhone应用程序的单元测试

MiK*_*iKL 16 iphone xcode unit-testing ocunit ios

注意:现在单元测试更容易设置.本教程与Xcode版本5及更高版本无关.

我花了很长时间,但我终于设法使它适用于我的项目.为了创建"逻辑"测试,我遵循Apple关于创建逻辑测试的指导原则.一旦您了解在构建期间运行逻辑测试,这就可以正常工作.

为了能够调试这些测试,需要创建一个可以调用这些测试的自定义可执行文件.本文通过对所著的Grokking可可博客肖恩·米塞利提供的所有信息来做到这一点.然而,它并没有立即取得成功,需要进行一些调整.

我将介绍Sean教程中提供的主要步骤,提供一些"for dummies"大纲,这花了我一些时间来弄清楚:

  1. 设置包含单元测试的目标但不运行它们
  2. 设置otest可执行文件以运行测试
  3. 设置otest环境变量,以便otest可以找到您的单元测试

使用XCode 3.2.5执行以下操作

XCode 4的注意事项

在XCode 4中,可以直接调试单元测试.只需编写测试,将其作为测试之一添加到目标并在其中设置断点.就这样.会有更多.

第1步 - 设置目标

  1. 复制位于项目目标下的单元测试目标.这也将创建单元测试产品(.octest文件)的副本.在下图中,"LogicTest"是原始目标.
  2. 将单元测试目标和单元测试产品(.octest文件)重命名为相同的名称.在下图中,"LogicTestsDebug"是重复的目标.
  3. 删除新目标的RunScript阶段

两者的名字可以是任何东西,但我会避免空格.

在此输入图像描述

第2步 - 设置otest

这里最重要的一点是获得正确的otest,即适用于您当前的iOS而不是默认的Mac版本.这在Sean的教程中有详细描述.以下是一些帮助我做好准备的细节:

  1. Go Project-> New Custom Executable.这将弹出一个窗口,提示您输入可执行文件名和可执行文件路径.
  2. 输入您想要的任何名称.
  3. 复制粘贴路径到您的iOS otest可执行文件.在我的例子中,这是/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator4.2.sdk/Developer/usr/bin/otest
  4. 按enter键.这将带您进入可执行文件的配置页面.
  5. 此时唯一要改变的是选择"路径类型:相对于当前SDK".不要输入路径,这是在步骤3完成的. 在此输入图像描述

第3步 - 设置otest参数和环境变量

讽刺的论点很容易设置......但事实证明这是我最大的问题.我最初将我的逻辑测试目标命名为"LogicTests Debug".使用此名称和"LogicTests Debug.octest"(带引号)作为otest的参数我保持otest终止与退出代码1并且永远不会停止到我的代码...

解决方案:目标名称中没有空格!

otest的论据是:

  1. -SenTest Self(或全部或测试名称 - 在终端中键入man otest以获取列表)
  2. {LogicTestsDebug} .octest - 需要用逻辑测试包名称替换{LogicTestsDebug}.

以下是复制/粘贴的环境变量列表:

  • DYLD_ROOT_PATH:$ SDKROOT
  • DYLD_FRAMEWORK_PATH:"$ {BUILD_PRODUCTS_DIR}:$ {SDK_ROOT}:$ {DYLD_FRAMEWORK_PATH}"
  • IPHONE_SIMULATOR_ROOT:$ SDKROOT
  • CFFIXED_USER_HOME:"$ {HOME} /图书馆/应用程序支持/ iPhone模拟器/用户"
  • DYLD_LIBRARY_PATH:$ {BUILD_PRODUCTS_DIR}:$ {DYLD_LIBRARY_PATH}
  • DYLD_NEW_LOCAL_SHARED_REGIONS:是的
  • DYLD_NO_FIX_PREBINDING:是的

请注意,我也尝试过DYLD_FORCE_FLAT_NAMESPACE,但这只是造成了骚乱.

在此输入图像描述

第4步 - 运行您的otest可执行文件

要运行您的otest可执行文件并开始调试您的测试,您需要:

  1. 将您的活动目标设置为您的单元测试目标(在我的情况下为LogicTestsDebug)
  2. 将活动可执行文件设置为您的可执行文件

您可以使用断点构建和运行可执行文件并调试测试.

作为旁注,如果您在运行otest可执行文件时遇到问题,则可能与以下内容有关:

  1. 路径错误.我最初有很多问题,因为我指的是mac otest.我一直在使用终止代码6启动时崩溃.
  2. 错误的论点.直到我从bundle(.octest)名称中删除了空格,我一直在用退出代码1进行骚乱.
  3. 环境变量中的路径错误.肖恩教程有很多后续问题,可以提供一些其他人尝试过的见解.我现在的套装似乎工作,所以我建议你从这开始.

您可能会在控制台中收到一些消息,这些消息可能会导致您认为环境变量存在问题.您可能会注意到有关CFP参考的消息.此消息不会阻止测试正常运行,因此如果您在运行otest时遇到问题,请不要关注它.

在此输入图像描述

一旦一切正常,您将能够在测试中的断点处停下来.

在此输入图像描述

最后一件事...

我在很多博客上都看到,集成的XCode SenTestKit的主要限制是在构建应用程序时无法运行测试.事实证明这实际上很容易管理.您只需将Logic测试包添加为应用程序项目的依赖项.这将确保在构建应用程序之前构建逻辑测试包,即运行所有测试.

为此,您可以将逻辑测试包拖放到应用程序目标上.

在此输入图像描述

MiK*_*iKL 7

这篇文章的目的是作为"操作方法",而不仅仅是一个真正的问题.因此,这个答案只是为了让我将"操作方法"标记为"已回答".这可能会被社区标记为不正常.我想知道在哪里发布未来的"操作方法"文章.

关于这个主题的最后一点说明.对于那些仍然怀疑写单元测试是否值得的人我肯定会说是的!

我目前正在使用CoreData编写应用程序并从Web服务检索数据(xml解析).可以测试和调试完整的模型,而无需:

  1. 在模拟器或设备上运行实际应用程序.不必使用该设备来运行测试是一个巨大的时间.这是每次运行2分钟到5秒之间的差异.
  2. 在测试模型时无需创建视图或控制器.完整的开发和测试只能在第一次迭代中关注模型.一旦模型被清除以进行集成,其余的开发可以遵循.

要调试xml解析,我可以简单地使用我完全控制的"硬编码"文件.

当然,在您在代码中实现功能时,要编写测试.在整个应用程序的调试方面,它确实节省了时间.

Voilà,我会留下它.

  • 再次感谢您的操作方法.StackOverflow是发布此类文章的绝佳场所.我只是建议提出一个问题(在这种情况下"我如何运行和调试iPhone应用程序的单元测试?")然后编写how-to文章作为您自己问题的答案.我知道你只能在48小时之后将其标记为答案,但这似乎是最好的方式来发布操作规则的方法和游戏...对不起批评你的帖子,我知道你只是在尝试帮助. (2认同)