我有一个界面,例如:
public interface Thing {
FrobResult frob(FrobInput);
}
我尝试测试的该界面的几个实现(例如NormalThing
,ImmutableThing
,AsyncThing
)。
我的许多测试方法都是关于确保接口正确实现,因此在每个Thing
实现中都是重复的。在JUnit 3中,一个常见的解决方案是创建一个基类(扩展TestCase
),然后由每个实现类进行子类化。但这是JUnit 4的正确方法吗?
(我相信)优先顺序的可能替代方案:
Cut'n'paste重复的测试方法。根本不干,但我认为在测试中不如在生产代码中那么令人担忧。
使用@Test
方法创建一个抽象类,并为每个实现测试类创建子类。 (通常在JUnit 3测试中看到 - 这仍然是JUnit 4中的一个好方法吗?)
将常用测试方法放入辅助类中,并在每个实现上调用它。 (组成而不是继承。)
做#3的最佳做法是什么?也许每个实现参数化的@RunWith(Parameterized.class)
测试?或者有更好的方法来实现这一目标吗?
答案 0 :(得分:6)
是的,这是创建基类的正确方法,然后由JUnit4中的每个实现类进行子类化。
我更喜欢接口的基本测试类是抽象,即你的“替代”2,因为我在模拟测试代码的生产代码中的继承层次结构方面有很好的经验。因此,如果您有 I
接口和实施S1
,S2
和S3
,则可以创建抽象测试类 {{1} } 以及测试类TestI
,TestS1
和TestS2
。
测试用例应该说,即讲故事。通过选择 - 一如既往 - 仔细地使用方法名称并仅使用干净的行为子类型,继承不会混淆这一点。
答案 1 :(得分:1)
我对JUnit和TestNG测试用例使用#2方法。这是最方便和易于维护的。它也很容易接受(因为它原生于OOD以具有通用方法的基类)。 对我来说,单元测试类与常规项目类没有什么不同......所以我确实应用了类似的设计考虑因素。