programing

Junit @Before/@After는 어떤 순서로 호출됩니까?

goodcopy 2022. 10. 7. 21:42
반응형

Junit @Before/@After는 어떤 순서로 호출됩니까?

Integration Test Suite 。는 나나 a a a가 있다IntegrationTestBase내내모 、 험험을을는수 。에는 " " " 가 .@Before )public void setUp() 및 )의 개요@After )public void tearDown()API DB입니다.이 두 콜을 발신하고 .super.setUp() ★★★★★★★★★★★★★★★★★」super.tearDown()그러나 누군가가 슈퍼에 전화하는 것을 잊었거나 잘못된 장소에 전화를 걸었을 때 예외가 발생하여 최종적으로 슈퍼에 전화하는 것을 잊었을 경우 문제가 발생할 수 있습니다.

은...을 입니다.setUp ★★★★★★★★★★★★★★★★★」tearDown 에서의 메서드final 우리만의 됩니다.@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.

@Before슈퍼클래스의 메서드는 현재 클래스에서 오버라이드되지 않는 한 현재 클래스의 메서드보다 먼저 실행됩니다.하다

다음과 같습니다@After.

@After슈퍼클래스에서 선언된 메서드는 현재 클래스에서 재정의되지 않는 한 현재 클래스의 메서드 이후에 실행됩니다.

전에 날 물었던 한 가지 잠재력이 있어

하나 @Before입니다. 클래스의 입니다.그 이유는 실행 순서 때문입니다.@Before클래스 내에서 정의된 메서드는 보증되지 않습니다.그런 을 '아주머니'라고 .setUpTest()

@Before라고 기재되어 있습니다.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();
    ...
  }
}

@Before ★★★★★★★★★★★★★★★★★」@After올바른 결론은 방법에 고유한 이름을 붙이는 것입니다.테스트에서 사용하는 패턴은 다음과 같습니다.

public abstract class AbstractBaseTest {

  @Before
  public final void baseSetUp() { // or any other meaningful name
    System.out.println("AbstractBaseTest.setUp");
  }

  @After
  public final void baseTearDown() { // or any other meaningful name
    System.out.println("AbstractBaseTest.tearDown");
  }
}

그리고.

public class Test extends AbstractBaseTest {

  @Before
  public void setUp() {
    System.out.println("Test.setUp");
  }

  @After
  public void tearDown() {
    System.out.println("Test.tearDown");
  }

  @Test
  public void test1() throws Exception {
    System.out.println("test1");
  }

  @Test
  public void test2() throws Exception {
    System.out.println("test2");
  }
}

결과적으로 주다

AbstractBaseTest.setUp
Test.setUp
test1
Test.tearDown
AbstractBaseTest.tearDown
AbstractBaseTest.setUp
Test.setUp
test2
Test.tearDown
AbstractBaseTest.tearDown

접근법의 : :AbstractBaseTest는 understand를 수 .setUp/tearDown 하고할 수 있어요.만약 그들이 원한다면, 그들은 정확한 이름을 알아야 하고 할 수 있다.

(약함) 이 접근법의 단점: 사용자는 자신의 작업 전후에 어떤 일이 일어나고 있는지 알 수 없습니다.setUp/tearDown그들은 이러한 것들이 추상적인 계층에 의해 제공된다는 것을 알아야 한다.하지만 그게 그들이 추상적인 수업을 사용하는 이유라고 생각합니다.

설정을 전환하면 기본 클래스의 추상화를 선언하고 하위 클래스가 기본 클래스의 주석 있는 setUp 및 tearDown 메서드에서 호출되는 setUp 및 tearDown 메서드(주석 없음)를 선언하도록 할 수 있습니다.

사용할 수 있습니다.@BeforeClass을 확실히 하기 위한 주석setup()항상 먼저 호출됩니다.마찬가지로, 다음을 사용할 수 있습니다.@AfterClass을 확실히 하기 위한 주석tearDown()항상 꼴찌라고 불립니다.

이는 보통 권장되지 않지만 지원됩니다.

원하는 것은 아니지만 테스트가 실행되는 내내 DB 연결을 열어둔 다음 마지막으로 완전히 종료합니다.

태그라인 질문에 대한 답변은 아니지만 질문 본문에 언급된 문제에 대한 답변입니다.@Before 또는 @After를 사용하는 대신 @org.junit을 사용하는 것을 검토합니다.규칙이 더 유연해지기 때문에 규칙을 정하세요.External Resource(4.7 기준)는 연결을 관리할 때 가장 관심을 갖는 규칙입니다.또한 규칙 실행 순서를 보장하려면 규칙 체인을 사용합니다(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);
     }
 }

언급URL : https://stackoverflow.com/questions/6076599/what-order-are-the-junit-before-after-called

반응형