2009-12-17 21 views
27

Khi sử dụng phương pháp này bên dưới, bằng cách thiết lập jUnit with Suites. Chúng tôi đã gặp sự cố khi tất cả @BeforeClass trong mọi Lớp kiểm tra sẽ được thực thi trước khi bất kỳ thử nghiệm nào bắt đầu thực thi. (Đối với mỗi tệp TestClass của @BeforeClass chạy, sau khi chúng đã thực thi, nó bắt đầu thực thi tệp MyTest.class đầu tiên @Test)JUnit 4 @BeforeClass & @AfterClass khi sử dụng Suites

Điều này sẽ khiến chúng tôi phân bổ nhiều tài nguyên và bộ nhớ. Suy nghĩ của tôi là nó phải sai, không phải mỗi @BeforeClass chỉ chạy trước khi lớp thi thực tế được thực hiện, không phải khi Suite được bắt đầu?

@RunWith(Suite.class) 
@Suite.SuiteClasses({ MyTests.class, Mytests2.class, n1, n2, n }) 
public class AllTests { 
    // empty 
} 


public class MyTests { // no extends here 
    @BeforeClass 
    public static void setUpOnce() throws InterruptedException { 
     ... 
    @Test 
     ... 

public class MyTests2 { // no extends here 
    @BeforeClass 
    public static void setUpOnce() throws InterruptedException { 
     ... 
    @Test 
     ... 
+0

Họ thực hiện trước khi kiểm tra từng lớp học, hay tất cả đều được thực hiện duy nhất trước khi là người đầu tiên (nhưng sau đó thứ hai là chạy mà không cần chạy tất cả @BeforeClass lần nữa)? Sau này có vẻ OK khi @BeforeClass được chạy trước các phương thức @Test trong thử nghiệm đó. Số lượng bộ nhớ sẽ không thay đổi tôi giả sử, trừ khi bạn dọn dẹp sau mỗi bài kiểm tra của mỗi lớp (và những điều này cũng chỉ xảy ra sau khi toàn bộ bộ được hoàn thành). –

+1

Điều tôi nhận được ngay bây giờ là mỗi @BeforeClass được chạy trước tiên. @BeforeClass (Mytests) @BeforeClass (Mytests2) @Test (MyTests) @Test (MyTests2) Tại quan điểm của tôi, điều này là không đúng. Sửa lỗi cho tôi nếu tôi sai, nhưng một số thứ phải được thiết lập sai để gây ra sự cố này. –

Trả lời

43

Viết phương thức @BeforeClass trong lớp AllTests sẽ được thực hiện khi bộ phần mềm được bắt đầu.

public class MyTests1 { 
    @BeforeClass 
    public static void beforeClass() { 
     System.out.println("MyTests1.beforeClass"); 
    } 

    @Before 
    public void before() { 
     System.out.println("MyTests1.before"); 
    } 

    @AfterClass 
    public static void afterClass() { 
     System.out.println("MyTests1.AfterClass"); 
    } 

    @After 
    public void after() { 
     System.out.println("MyTests1.after"); 
    } 

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

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



public class MyTests2 { 
    @BeforeClass 
    public static void beforeClass() { 
     System.out.println("MyTests2.beforeClass"); 
    } 

    @Before 
    public void before() { 
     System.out.println("MyTests2.before"); 
    } 

    @AfterClass 
    public static void afterClass() { 
     System.out.println("MyTests2.AfterClass"); 
    } 

    @After 
    public void after() { 
     System.out.println("MyTests2.after"); 
    } 

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

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




@RunWith(Suite.class) 
@Suite.SuiteClasses({ MyTests1.class, MyTests2.class }) 
public class AllTests { 

    @BeforeClass 
    public static void beforeClass() { 
     System.out.println("AllTests.beforeClass"); 
    } 

    @Before 
    public void before() { 
     System.out.println("AllTests.before"); 
    } 

    @AfterClass 
    public static void afterClass() { 
     System.out.println("AllTests.AfterClass"); 
    } 

    @After 
    public void after() { 
     System.out.println("AllTests.after"); 
    } 

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

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

} 

OUTPUT

AllTests.beforeClass 
MyTests1.beforeClass 
MyTests1.before 
MyTests1.test1 
MyTests1.after 
MyTests1.before 
MyTests1.test2 
MyTests1.after 
MyTests1.AfterClass 
MyTests2.beforeClass 
MyTests2.before 
MyTests2.test1 
MyTests2.after 
MyTests2.before 
MyTests2.test2 
MyTests2.after 
MyTests2.AfterClass 
AllTests.AfterClass 

hth

+4

'AllTests.test1()' và '" AllTests.test2() 'và' "AllTests.test2()' không bao giờ được thực thi? – Theodor

+0

@nayakam Điều đó sẽ giải quyết được vấn đề ngay lập tức, nhưng tôi nghĩ rằng các lớp kiểm tra cá nhân hoặc phụ không thể chạy trên chúng sở hữu? – nsandersen

-4

Tôi nghĩ, @BeforeClass thực hiện tại instanciation.

+0

Nó không. "Chú thích phương thức public static void no-arg với @BeforeClass khiến nó được chạy một lần trước bất kỳ phương thức thử nào trong lớp. Các phương thức @BeforeClass của các lớp bậc trên sẽ được chạy trước các lớp hiện tại." (Nguồn: tài liệu JUnit) – Jorn

+0

Chỉ cần thêm một số thông tin bổ sung cho những người gặp sự cố với bộ nhớ. JUnit sẽ lưu tất cả các trạng thái khi chạy, và cũng sẽ lưu tất cả các biến tĩnh cho đến khi tất cả các kiểm tra JUnit đã thực thi. Đây cũng là một vấn đề lớn kể từ khi chúng tôi đang chạy giữa 1000-6000 bài kiểm tra JUnit. Điều này bởi vì nó cần nó để hiển thị kết quả ở cuối. –

1

Tôi không quá quen thuộc với @RunWith trong JUnit, vì vậy tôi có thể đã làm điều gì đó sai, nhưng tôi dường như không thể tái tạo hành vi mà bạn mô tả. Với lớp:

@RunWith(Suite.class) 
@Suite.SuiteClasses({ FirstTest.class, SecondTest.class, ThirdTest.class }) 
public class AllTests { 
    // empty 
} 

Và FirstTest.java tìm kiếm như thế này:

public class FirstTest { 
    @BeforeClass 
    public static void doBeforeClass() { 
     System.out.println("Running @BeforeClass for FirstTest"); 
    } 

    @Test 
    public void doTest() { 
     System.out.println("Running @Test in " + getClass().getName()); 
    } 
} 

... với SecondTest.java và ThirdTest.java khá nhiều giống nhau. Tôi nhận được kết quả thử nghiệm:

Running @BeforeClass for FirstTest 
Running @Test in FirstTest 
Running @BeforeClass for SecondTest 
Running @Test in SecondTest 
Running @BeforeClass for ThirdTest 
Running @Test in ThirdTest 

Đây là với JUnit 4.5.0 (mặc định JUnit trong Eclipse 3.5.1) trên JDK 1.6.0_12 của Sun. Bạn có thể nhận ra bất kỳ sự khác biệt nào trong ví dụ của tôi từ bạn không? Có lẽ một JDK/JVM khác nhau? Tôi không biết đủ về nội bộ của JUnit để biết liệu đây có phải là một yếu tố hay không.

+0

Như bạn mô tả, là những gì tôi đã có nghĩa vụ phải nhận được cũng có. Nhưng tôi nhận được một loạt @BeforeClass đầu tiên, sau đó tôi thấy @Test đầu tiên, @Test và vân vân. Sử dụng JDK 1.6.0_17 của Sun, Eclipse 3.5, nhưng sau đó các thử nghiệm Chức năng của chúng tôi được thực hiện, chúng tôi đang sử dụng kiến, chạy maven. Một số điều này có thể ảnh hưởng đến kết quả không? Nếu tôi thiết lập nó trong Eclipse và chạy nó hoạt động, có vẻ như vấn đề này là phần nào trong kiến ​​hoặc quạ. –

+0

Xin lỗi, thực sự không thể giúp bạn chạy JUnit trong kiến ​​hoặc quạ. Mặc dù tôi đã xuất tệp build.xml cho ví dụ tôi đã sử dụng và chạy nó với mục tiêu kiểm tra, và có hành vi mà bạn đang tìm kiếm, vì vậy tôi nghi ngờ có gì đó sai với nhiệm vụ kiến ​​JUnit. * Nhún nhún * – Grundlefleck

Các vấn đề liên quan