2010-04-14 2 views
124

JUnit의 적절한 사용 (또는 적어도 설명서)이 매우 혼란 스럽습니다. 이 질문은 향후 참조 및 실제 질문으로 사용됩니다.JUnit 혼동 : 'extends TestCase'또는 '@Test'를 사용 하시겠습니까?

내가 제대로 이해했다면, 작성하고 JUnit 테스트를 실행하는 두 가지 방법이 있습니다 : 시험 방법을가의 TestCase를 확장하는 클래스를 작성하고 시작합니다

접근법 A (JUnit을 3 스타일) 단어는 test입니다. Eclipse에서 JUnit Test로 클래스를 실행하면 test이라는 단어로 시작하는 모든 메소드가 자동으로 실행됩니다.

import junit.framework.TestCase; 

public class DummyTestA extends TestCase { 

    public void testSum() { 
     int a = 5; 
     int b = 10; 
     int result = a + b; 
     assertEquals(15, result); 
    } 
} 

접근 B (JUnit을 -4- 스타일)는 '정상'클래스를 작성하고 상기 방법에 주석을 붙일 @Test. 단어 test으로 메소드를 시작할 필요는 없습니다.

import org.junit.*; 
import static org.junit.Assert.*; 

public class DummyTestB { 

    @Test 
    public void Sum() { 
     int a = 5; 
     int b = 10; 
     int result = a + b; 
     assertEquals(15, result); 
    } 
} 

두 가지를 혼용하는 것은 좋지 않은 것처럼 보입니다. this stackoverflow question :

이제 내 질문 (들) :

  1. 가 선호하는 방식 무엇입니까, 또는 때 대신 다른 중 하나를 사용해야합니까?
  2. 접근 방식 B는 @Test(expected = ArithmeticException.class)과 같이 @Test 주석을 확장하여 예외를 테스트 할 수 있습니다. 그러나 접근법 A를 사용할 때 예외를 테스트하려면 어떻게해야합니까?
  3. 방법 A를 사용하는 경우, 그룹화 할 수 있습니다 이런 테스트 스위트의 테스트 클래스의 수 :


    suite.addTestSuite(DummyTestA.class);
    suite.addTestSuite(DummyTestAbis.class);

    TestSuite suite = new TestSuite("All tests"); 그러나 이것은 (접근 B와 함께 사용할 수 없습니다 각 테스트 클래스는 TestCase를 서브 클래스 화해야하기 때문에). 접근법 B의 테스트를 그룹화하는 적절한 방법은 무엇입니까?

편집 : 나는에의 JUnit 버전을 추가 한 모두 내가 좀 더 유연하게 찾을 수 있기 때문에 내가 JUnit 4에서는 (주석 방식)에 대한 선호가

답변

96

구분은 오히려 간단하다

  • TestCase 확장이있다 JUnit 3에서 작성되었습니다 (물론 JUnit 4에서 계속 지원됩니다).
  • @Test 주석을 사용하는 것은 JUnit 4에서 소개 한 방식입니다.

일반적으로 JUnit 3 (및/또는 Java 5 이전의 Java 버전)과의 호환성이 필요하지 않으면 주석 경로를 선택해야합니다.

  • @Test annotaton 더 명시하고
  • 여러 방법이 @Before/@BeforeClass로 주석 할 수있다 (예를 들어,이 모든 테스트를 위해이 방법을 검색하기 쉽습니다) 도구에서 지원하는 것이 더 쉽습니다 : 새로운 방법은 몇 가지 장점이 있습니다 및 @After/@AfterClass@Ignored 주석에 대한 ExpectedException
  • 지원과 같은 것들에 @Rule annotations에 대한 더 많은 유연성을
  • 지원을 제공
  • ,536 JUnit가 3 TestCase에서 예상 예외를 테스트하려면 @RunWith

를 사용하여 다른 테스트 주자

  • 지원은 텍스트가 명시 적으로 만들어야 할 것입니다.

    public void testMyException() { 
        try { 
        objectUnderTest.myMethod(EVIL_ARGUMENT); 
        fail("myMethod did not throw an Exception!"); 
        } catch (MyException e) { 
        // ok! 
        // check for properties of exception here, if desired 
        } 
    } 
    
  • +0

    유용하고 철저한 답변이지만 "예외 메시지 확인"을 완전히 이해하지 못했습니다. 하드 코딩 된 문자열을 확인하는 것은 유지 보수의 악몽이 될 것입니다. "특정 예외 유형의 등록 정보 확인"을 의미해야합니다. – thSoft

    +3

    @thSoft : 자주 사용되는 것은 아니지만 때로는 예를 들어 예외 필드에 해당 예외 필드가 포함되도록하고 싶습니다. 그런 다음 간단한'assertTrue (e.getMessage(). contains ("foo"))'가 유용 할 수 있습니다. –

    +1

    JUnit4조차도 메시지 나 예외의 다른 속성 (원인 등)을 확인해야 할 때 중요한 관용구입니다. 'expected' 메쏘드는 타입을 검사합니다. – Yishai

    21

    접근한다.당신의 JUnit 4에서 테스트 스위트를 구축하려면

    , 모든이 같은 테스트를 그룹화 클래스 만들 수 있습니다

    import org.junit.runner.RunWith; 
    import org.junit.runners.Suite; 
    import org.junit.runners.Suite.SuiteClasses; 
    
    
    @RunWith(Suite.class) 
    @SuiteClasses({ 
        Test1.class, 
        Test2.class, 
        Test3.class, 
        Test4.class 
    })public class TestSuite 
    { 
    /* empty class */ 
    } 
    
    1
    1. 은 "선호"접근 방식은

    2. 당신은을 사용할 수 있습니다 (두 번째 질문 참조) 그들은 쉽게 많은 것들을 할 Junit와 4 년부터 도입 된 주석을 사용하는 것입니다 그에 대한 간단한 try/catch 블록은 :

    
    public void testForException() { 
        try { 
         Integer.parseInt("just a string"); 
         fail("Exception should have been thrown"); 
        } catch (final Exception e) { 
         // expected 
        } 
    } 
    
    3

    당신은 더 나은의 JUnit 4를 사용해야합니다.

    많은 프레임 워크가 JUnit 3.8 지원을 비하하기 시작했습니다.

    이 봄 3.0 참조 문서에서입니다 :

    [주의] 기존의 JUnit 계층 구조는 일반적으로

    를 더 이상 사용되지 않습니다 3.8 클래스, 당신은 항상 최신 안정 버전을 사용하려고합니다 새로운 무언가를 시작할 때 프레임 워크.

    14

    질문에 대답 할 수없는 부분이 있습니다. "접근 B의 테스트를 그룹화하는 적절한 방법은 무엇입니까?"

    공식적인 대답은 @RunWith (Suite.클래스)를 작성한 다음 @ Suite.SuiteClasses 주석을 사용하여 클래스를 나열하십시오. 이것이 JUnit 개발자들이하는 일입니다 (스위트의 모든 클래스를 수동으로 나열). 여러 가지면에서이 접근법은 개선점입니다. 스위트 및 애프터 비헤이비어 동작 전에 추가하는 것이 쉽고 직관적입니다 (@RunWith로 주석 된 클래스에 @BeforeClass 및 @AfterClass 메서드를 추가하면됩니다. 이전 TestFixture보다 훨씬 낫습니다).).

    그러나 주석에는 역동적으로 클래스 목록을 만들 수 없으므로이 단계를 거쳐야합니다.이 문제를 해결하기 위해서는 약간 추한 것입니다. Suite 클래스를 서브 클래스 화하고 서브 클래스에서 클래스 배열을 동적으로 생성하여 Suite 생성자에 전달해야하지만, Suite의 다른 하위 클래스 (예 : 카테고리)가이 클래스와 함께 작동하지 않는다는 점에서 불완전한 솔루션입니다 동적 테스트 클래스 컬렉션을 지원하지 않습니다.

    +1

    +1. TestSuite에 테스트를 추가하는 역동적 인 솔루션을 작성하는 작업을 시작한 후에는 각 테스트에서 TestCase를 확장해야했습니다. JUnit4 주석을 사용하여 예상되는 예외를 정의하는 작업 단위 테스트가 손상되었습니다. 테스트 스위트를 동적으로 채우는 방법에 대한 필자의 탐구가이 스레드, 특히 JUnit 3을 계속 사용하는 몇 가지 바람직한 이유 중 하나라고 생각하는 답변으로 연결되었습니다. – 8bitjunkie

    관련 문제