在这里寻找一些实用的建议以及人们在类似情况下的任何经历。
我们使用BDD / TDD sytle方法来构建我们的软件(相当大/复杂的应用程序)最终结果是......从业务需求派生的行为规范(Given / When / Then style),反映这些和反映测试要求的代码。
然而,最近我们的测试部门已开始运行集成测试,可以理解的是他们希望使用我们(已经通过的)业务逻辑代码来设置和拆除测试状态(而不是直接处理数据库)主要关注通过应用程序的UI进行测试,并且不想花费一整天的时间来争论数据库。
问题是,某些实体存储库没有删除方法,因为尚未针对这些方法表达业务需求。许多人都有存档/恢复/备份等(并且可能在待办事项上有待删除的暂停)。
所以现在我们有一个测试部门。删除要求(但与业务用户故事冲突的要求)
所以....我的问题是......如果我要专门为测试部门添加方法......那么处理这些方法的最佳方法是什么。我知道这在“TDD乌托邦”中通常被认为是不好的做法,但实际上,你是如何处理这种冲突的呢?
我的第一个想法是使用命名...
void TestOnly_Delete(Guid id){}
...属性...
[TestOnly]
void Delete(Guid id){}
...或编译器指令......
#if TESTBUILD
void Delete(Guid id){}
#endif
因此,开发人员至少可以知道不要调用TestOnly方法,并且最多不会在生产版本中部署测试方法。
...或者只是作弊并添加一个用户故事来管理它; - )
感谢任何经验或建议?
提前致谢。
答案 0 :(得分:4)
你的第一个问题应该是添加此功能是否会增强或恶化当前的API? TDD中的一个典型场景是(最初)只有出于可测试性原因才需要类成员,但它符合所有正常的API设计指南,因此它没有任何危害(并且通常随后在生产代码中也是有价值的补充)。
如果这是真的,那么只要你能轻易地添加它 。
然而,有时情况正好相反。在这种情况下,您必须抵制添加成员的冲动。但是,通常您可以按照Open/Closed Principle并打开API,以便其他人能够添加所需的功能。 Testability is really just another word for the Open/Closed Principle
在您的情况下,最简单的解决方案可能只是确保有问题的类被解封,然后要求测试部门从这些类派生并自己实现功能。如果他们没有这种能力,那么你可以为他们做,同时仍然保持子类只测试。
答案 1 :(得分:1)
在我的代码中,我创建了一个子类:例如,如果我有一个DataLayer
类,它具有访问数据层的所有公共方法,那么我可以使用Test_DataLayer
子类对其进行子类化,它继承了DataLayer
中的方法,并进一步实现了您可能需要的任何其他方法,如Delete
,并且其实现可以访问基类的内部或受保护方法。
答案 2 :(得分:1)
我通常最终得到一个“仅限测试”的项目/库,其中包含我测试所需的任何模拟/助手类。在这个模拟库中添加必要的类/方法 - 生产代码中没有包含它 - 似乎很适合这个要求。如果您还没有这样的库,并且不想创建一个库,那么我会在可能的情况下标记内部方法,并仅将它们暴露给测试框架。你没有指定平台,但我知道这可以通过C#/ .NET实现,而且我经常使用这种能力让我的测试可以访问那些在库外无法使用的方法。
另一方面,我会说测试人员的需求分析与实际客户一样多。就像我们有一些纯粹满足我们开发需求的要求一样,我们也有一些测试要求。正如您所发现的那样,诀窍是以尽可能满足利益相关者所有需求的方式开发代码。当需求发生冲突时,我们会尝试尽可能使用最佳折衷方案。 IMO可以从仅测试库中删除,这是对客户对数据安全性的需求的合理折衷(无删除)。
答案 3 :(得分:0)
这是一个有趣的问题。我有一些想法,但不确定它是否能解决你的问题。
我将亲自创建一个继承自您已经拥有的实体的明确接口集,例如IIntTest_Customer:ICustomer,并在那里定义delete方法。如果可能的话,尝试将所有这些接口放在单独的项目中,这样开发人员甚至不会从通常的项目中引用它并避免意外使用它们。然后,测试部门将使用此特定的内部测试接口进行测试。
要实现这一点,您可能必须重构当前代码并更改实体以实现这些内部测试接口,而使用继承层次结构,所有现有代码仍然可以工作,引用基接口。
答案 4 :(得分:0)
我永远不会在我的代码中添加删除或其他清理方法,只是为了支持自动化测试。
有很多选择,从智能交易管理到数据库的自动恢复。