[java] Junit @ Before / @ After叫什麼命令?



Answers

一個潛在的問題曾經困擾我:

我喜歡在每個測試類中至多有一個@Before方法,因為不能保證運行在類中定義的@Before方法的順序。 通常,我會調用setUpTest()這樣的方法。

但是,雖然@Before被記錄為The @Before methods of superclasses will be run before those of the current class. No other ordering is defined. The @Before methods of superclasses will be run before those of the current class. No other ordering is defined. ,這僅適用於每個標有@Before方法在類層次結構中具有唯一名稱的情況。

例如,我有以下幾點:

public class AbstractFooTest {
  @Before
  public void setUpTest() { 
     ... 
  }
}

public void FooTest extends AbstractFooTest {
  @Before
  public void setUpTest() { 
    ...
  }
}

我期望AbstractFooTest.setUpTest()FooTest.setUpTest()之前運行,但只執行FooTest.setupTest()AbstractFooTest.setUpTest()根本沒有被調用。

代碼必須修改如下才能工作:

public void FooTest extends AbstractFooTest {
  @Before
  public void setUpTest() {
    super.setUpTest();
    ...
  }
}
Question

我有一個集成測試套件。 我有一個IntegrationTestBase類,用於擴展我的所有測試。 這個基類有一個@Beforepublic void setUp() )和@Afterpublic void tearDown() )方法來建立API和數據庫連接。 我一直在做的是重寫每個測試用例中的這兩個方法,並調用super.setUp()super.tearDown() 。 然而,如果有人忘記調用super或將它們放在錯誤的地方並拋出異常,並且忘記在finally或其他地方調用super,這可能會導致問題。

我想要做的是在基類final上創建setUptearDown方法,然後添加我們自己註釋的@Before@After方法。 做一些初始測試時,它總是按以下順序調用:

Base @Before
Test @Before
Test
Test @After
Base @After

但我只是有點擔心,訂單不能保證,可能會導致問題。 我環顧四周,沒有看到有關這個問題的任何事情。 有誰知道我是否可以做到這一點,並沒有任何問題?

碼:

public class IntegrationTestBase {

    @Before
    public final void setUp() { *always called 1st?* }

    @After
    public final void tearDown() { *always called last?* }
}


public class MyTest extends IntegrationTestBase {

    @Before
    public final void before() { *always called 2nd?* }

    @Test
    public void test() { *always called 3rd?* }

    @After
    public final void after() { *always called 4th?* }
}



這不是對口號問題的回答,但它是問題主體中提到的問題的答案。 不要使用@Before或@After,而要使用@org.junit.Rule因為它給了你更多的靈活性。 如果您正在管理連接,則ExternalResource (從4.7開始)是您最感興趣的規則。 另外,如果您希望規則的保證執行順序使用RuleChain (從4.10開始)。 我相信當問這個問題時,所有這些都是可用的。 下面的代碼示例是從ExternalResource的javadocs複製的。

 public static class UsesExternalResource {
  Server myServer= new Server();

  @Rule
  public ExternalResource resource= new ExternalResource() {
      @Override
      protected void before() throws Throwable {
          myServer.connect();
         };

      @Override
      protected void after() {
          myServer.disconnect();
         };
     };

  @Test
  public void testFoo() {
      new Client().run(myServer);
     }
 }



如果反過來,可以聲明基類的抽象,並讓後代聲明setUp和tearDown方法(不帶註釋),這些方法在基類的帶註釋的setUp和tearDown方法中調用。






Related