假设我要测试以下通用工作流程:
CreateObject-> AddItemsToObject-> SaveObject-> ChangeObjectToFirstState-> ChangeObjectToSecondDependentOnBeingInFirstState->等等...
我应该:
A)为所有这些状态的整体编写一个测试用例-IE,CreateObject将测试对象是否正确创建,AddItemsToObject将使用所用代码CreateObject的副本,然后测试是否向对象添加项目如果处理正确,SaveObject将使用所使用代码AddItemsToObject的副本,然后将对象保存到数据库并测试是否正确保存了对象,等等。
B)为CreateObject编写测试用例,并成功返回一个创建的对象,然后AddItemsToObject将该对象用作要添加项目的对象,SaveObject将该对象用作要保存的对象,等等...
C)不必费心将链的每个步骤分成单独的测试用例,而只为每个完整链编写一个测试用例
我尝试搜索其他示例,但可能无济于事-如果已经彻底回答了该问题,请给我链接适当的问题:)
*编辑*
要重新措辞,以便更多的是一个问题:
是否有特定原因不是使用基于链的方法为工作流编写测试用例?
换句话说,对于多阶段工作流,是否有任何特定原因 not 在实现测试用例时首先调用测试用例以将对象从状态2推进到状态3将对象从3号州推进到4号州?
答案 0 :(得分:1)
TL; DR-不同级别的测试,单元(案例A)->集成(案例B)的组合是理想的方法。
我经常看到,将测试添加到代码库中比在单个工作项上花费更多时间。需要考虑许多变量,例如分配给测试的时间,系统的关键性,代码的复杂性等。
在您的示例中,从开发人员的角度来看,编写一个广泛的集成测试(案例C)几乎总是更简单,更快捷。但是,正如所指出的那样,这种方法也有缺点。仅举几例:1)如果失败,则将很难调试; 2)如果您的每个 n 函数都有例如2个代码路径,则需要2 ^ n测试用例涵盖所有路径。也就是说,集成/系统测试总是比没有测试要好。根据我的经验,在测试现有/旧版代码库时,它们是最有价值的东西。
另一方面,如果您有时间,编写针对特定功能的单元测试(案例A)是补充测试基础的绝佳方法。在这种情况下,使用上面概述的变量,您只需要2 * n个测试即可覆盖所有路径,并且一次测试失败将标识一个较小的向量用于调试。这里的一个好模式是使用一个像Moq这样的DI框架来隔离每个单独组件的逻辑。
Here's a more thorough conversation on unit vs. integration tests.
情况B也不一定是坏方法。它本质上是集成测试的一种形式,您可以在其中更深入地了解问题发生的位置。同样,这些是您需要在项目环境中做出的决定,同时要考虑到整个工作流程中每个功能的复杂性。