JUnit:使用构造函数而不是@Before
我正在使用JUnit 4.我看不到在构造函数中初始化或使用由@Before
注释的专用init函数之间的@Before
。 这是否意味着我不必担心呢?
有没有什么情况下@Before
不仅仅是在构造函数中进行初始化?
不,使用构造函数初始化您的JUnittesting夹具在技术上等同于使用@Before
方法(由于JUnit为每个@Test
创build一个testing类的新实例)。 唯一的(内涵)区别是它打破了@Before
和@After
之间的对称性,这可能会让一些人感到困惑。 恕我直言,最好遵守惯例(使用@Before
)。
还要注意的是,在JUnit 4和注释之前,有专门的setUp()
和tearDown()
方法 – @Before
和@After
注释取代了这些,但保留了底层的逻辑。 因此,使用注释还可以让从JUnit 3或更早版本迁移的人员更轻松。
@Before在某些情况下使用更有意义,因为它在类的构造函数之后被调用。 当你使用带有@Mock注释的Mockito这样的模拟框架时,这个区别是很重要的,因为你的@Before方法将在模拟初始化后被调用。 然后你可以使用你的mock为被testing的类提供构造函数参数。
在使用合作bean的unit testing中,我发现这是一个非常常见的模式。
这是一个(被公认为是人为的)例子:
@RunWith(MockitoJUnitRunner.class) public class CalculatorTest { @Mock Adder adder; @Mock Subtractor subtractor; @Mock Divider divider; @Mock Multiplier multiplier; Calculator calculator; @Before public void setUp() { calculator = new Calculator(adder,subtractor,divider,multiplier); } @Test public void testAdd() { BigDecimal value = calculator.add(2,2); verify(adder).add(eq(2),eq(2)); } }
我更喜欢将我的灯具声明为final,并将它们初始化为内联或构造函数,所以我不会忘记初始化它们! 但是,由于在@Before中引发的exception是以更加用户友好的方式处理的,我通常在@Before中初始化待testing的对象。
我更喜欢使用构造函数来初始化我的testing对象,因为它允许我使所有成员都成为final
以便IDE或编译器会告诉我何时构造函数忘记初始化成员并阻止其他方法设置它们。
恕我直言, @Before
违反了最重要的Java惯例之一,依靠构造函数来完全初始化对象!
@Before在任何@Test之前被调用,而不是每个Test-Class一次。
这可以用来重置/初始化每个特定的testing数据(如重置variables为一个特定的值等)。
在@Test方法执行之后,可以用同样的方式清理代码。
请参阅: http : //junit.sourceforge.net/javadoc/org/junit/Before.html
@Before
确实有道理,有几个原因。 它使您的testing代码更具可读性。 它匹配@After
注释,它负责释放已使用的资源,并且是@BeforeClass
注释的对应部分。
除了构造函数是ehere可以初始化@Rule对象的唯一方法之外没有任何区别:
public class TestClass { @Rule public SomeRule rule; public TestClass() { // code to initialize the rule field conf = new RuleConf() rule = new SomeRule(conf) } }