Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What's the best way to set up a per-test or per-class timeout when using <junit> in perBatch forkmode?

Tags:

I want to fail the build if anyone writes a test that takes longer than 1 second to run, but if I run in perTest mode it takes much, much longer.

I could probably write a custom task that parses the junit reports and fails the build based on that, but I was wondering if anyone knows or can think of a better option.

like image 711
Jun-Dai Bates-Kobashigawa Avatar asked Jan 05 '12 13:01

Jun-Dai Bates-Kobashigawa


People also ask

How will you set the timeout in test cases in JUnit?

JUnit provides a handy option of Timeout. If a test case takes more time than the specified number of milliseconds, then JUnit will automatically mark it as failed. The timeout parameter is used along with @Test annotation. Let us see the @Test(timeout) in action.

How will you set the timeout in test cases?

To specify the timeout period of a certain test case, “timeout” attribute is mentioned on the annotation @Test . Note that the timeout time is specified in milliseconds. In the above test, execution will be timed out after 500ms with the below message.

What applies the same timeout to every test method of a class?

What applies the same timeout to every test method of a class? Explanation: The timeout can be specified as a rule so that it is applied to every method. Explanation: The correct way to initialise a Timeout Rules is using the Timeout. seconds() function.


2 Answers

Reviving an old question since the answer doesn't provide an example.

You can specify timeout

  1. Per test method:

     @Test(timeout = 100) // Exception: test timed out after 100 milliseconds  public void test1() throws Exception {      Thread.sleep(200);  } 
  2. For all methods in a test class using Timeout @Rule:

     @Rule  public Timeout timeout = new Timeout(100);   @Test // Exception: test timed out after 100 milliseconds  public void methodTimeout() throws Exception {      Thread.sleep(200);  }   @Test  public void methodInTime() throws Exception {      Thread.sleep(50);  } 
  3. Globally for the total time to run all test methods in the class using a static Timeout @ClassRule:

     @ClassRule  public static Timeout classTimeout = new Timeout(200);   @Test  public void test1() throws Exception {      Thread.sleep(150);  }   @Test // InterruptedException: sleep interrupted  public void test2() throws Exception {      Thread.sleep(100);  } 
  4. And even apply timeout (either @Rule or @ClassRule) to all classes in your entire suite:

     @RunWith(Suite.class)  @SuiteClasses({ Test1.class, Test2.class})  public class SuiteWithTimeout {      @ClassRule      public static Timeout classTimeout = new Timeout(1000);       @Rule      public Timeout timeout = new Timeout(100);  } 

EDIT: timeout was deprecated recently to utilize this initialization

@Rule public Timeout timeout = new Timeout(120000, TimeUnit.MILLISECONDS); 

You should provide the Timeunit now, as this will provide more granularity to your code.

like image 61
Mifeet Avatar answered Sep 29 '22 19:09

Mifeet


If you use JUnit 4 and @Test, you can specifiy the timeout parameter that will fail a tests that's taking longer than specified. Downside for that is that you'd have to add it to every test method.

A probably better alternative is the use of a @Rule with org.junit.rules.Timeout. With this, you can do it per class (or even in a shared super class).

like image 40
ftr Avatar answered Sep 29 '22 20:09

ftr