protected void setUp() { System.setErr(new PrintStream(new ByteArrayOutputStream())); inputDir = new File("data"); inputDir = new File(inputDir, "xslt"); inputDir = new File(inputDir, "input"); }
在 JUnit 4 中,您仍然可以在每個測試方法運行之前初始化字段和配置環(huán)境。然而,完成這些操作的方法不再需要叫做 setUp(),只要用 @Before 注釋來指示即可,如下所示:
@Before protected void initialize() { System.setErr(new PrintStream(new ByteArrayOutputStream())); inputDir = new File("data"); inputDir = new File(inputDir, "xslt"); inputDir = new File(inputDir, "input"); }
甚至可以用 @Before 來注釋多個方法,這些方法都在每個測試之前運行:
@Before protected void findTestDataDirectory() { inputDir = new File("data"); inputDir = new File(inputDir, "xslt"); inputDir = new File(inputDir, "input"); } @Before protected void redirectStderr() { System.setErr(new PrintStream(new ByteArrayOutputStream())); }
清除方法與此類似。在 JUnit 3 中,您使用 tearDown() 方法,該方法類似于我在 XOM 中為消耗大量內存的測試所使用的方法:
protected void tearDown() { doc = null; System.gc(); }
對于 JUnit 4,我可以給它取一個更自然的名稱,并用 @After 注釋它:
@After protected void disposeDocument() { doc = null; System.gc(); }
與 @Before 一樣,也可以用 @After 來注釋多個清除方法,這些方法都在每個測試之后運行。
后,您不再需要在超類中顯式調用初始化和清除方法,只要它們不被覆蓋即可,測試運行程序將根據需要自動為您調用這些方法。超類中的 @Before 方法在子類中的 @Before 方法之前被調用(這反映了構造函數(shù)調用的順序)。@After 方法以反方向運行:子類中的方法在超類中的方法之前被調用。否則,多個 @Before 或 @After 方法的相對順序得不到保證。
套件范圍的初始化
JUnit 4 也引入了一個 JUnit 3 中沒有的新特性:類范圍的 setUp() 和 tearDown() 方法。任何用 @BeforeClass 注釋的方法都將在該類中的測試方法運行之前剛好運行一次,而任何用 @AfterClass 注釋的方法都將在該類中的所有測試都運行之后剛好運行一次。
例如,假設類中的每個測試都使用一個數(shù)據庫連接、一個網絡連接、一個非常大的數(shù)據結構,或者還有一些對于初始化和事情安排來說比較昂貴的其他資源。不要在每個測試之前都重新創(chuàng)建它,您可以創(chuàng)建它一次,并還原它一次。該方法將使得有些測試案例運行起來快得多。例如,當我測試調用第三方庫的代碼中的錯誤處理時,我通常喜歡在測試開始之前重定向 System.err,以便輸出不被預期的錯誤消息打亂。然后我在測試結束后還原它,如下所示:
// This class tests a lot of error conditions, which
// Xalan annoyingly logs to System.err. This hides System.err
// before each test and rest