0
0
JUnittesting~5 mins

TestInstance lifecycle per class in JUnit

Choose your learning style9 modes available
Introduction

Using TestInstance lifecycle per class helps run all tests in the same object. This saves time and lets tests share data easily.

When you want to share setup data between tests without recreating it each time.
When tests depend on some common state or resource initialized once.
When you want to reduce test execution time by avoiding repeated object creation.
When you want to keep test methods in the same instance to maintain state.
When using expensive setup operations that should run only once per class.
Syntax
JUnit
@TestInstance(TestInstance.Lifecycle.PER_CLASS)
public class YourTestClass {
    // test methods here
}

This annotation tells JUnit to create one test class instance for all tests.

Default lifecycle is PER_METHOD, which creates a new instance for each test method.

Examples
This example shows a test class using PER_CLASS lifecycle. The Calculator object is created once in @BeforeAll and used in all tests.
JUnit
@TestInstance(TestInstance.Lifecycle.PER_CLASS)
public class CalculatorTest {

    private Calculator calculator;

    @BeforeAll
    void setup() {
        calculator = new Calculator();
    }

    @Test
    void testAdd() {
        assertEquals(5, calculator.add(2, 3));
    }

    @Test
    void testSubtract() {
        assertEquals(1, calculator.subtract(3, 2));
    }
}
Here, the counter variable keeps its value between tests because the same instance is used.
JUnit
@TestInstance(TestInstance.Lifecycle.PER_CLASS)
public class CounterTest {

    private int counter = 0;

    @Test
    void testIncrement() {
        counter++;
        assertTrue(counter > 0);
    }

    @Test
    void testCounterValue() {
        assertEquals(1, counter);
    }
}
Sample Program

This test class uses PER_CLASS lifecycle. The count variable is initialized once before all tests. Each test changes count, and the changes persist between tests.

JUnit
import org.junit.jupiter.api.*;
import static org.junit.jupiter.api.Assertions.*;

@TestInstance(TestInstance.Lifecycle.PER_CLASS)
public class SampleTest {

    private int count = 0;

    @BeforeAll
    void init() {
        count = 10;
        System.out.println("BeforeAll: count = " + count);
    }

    @Test
    void testOne() {
        count++;
        System.out.println("TestOne: count = " + count);
        assertEquals(11, count);
    }

    @Test
    void testTwo() {
        count += 2;
        System.out.println("TestTwo: count = " + count);
        assertEquals(13, count);
    }
}
OutputSuccess
Important Notes

Use PER_CLASS lifecycle only when tests can safely share state to avoid flaky tests.

@BeforeAll methods can be non-static with PER_CLASS lifecycle, unlike the default PER_METHOD.

Be careful with shared mutable state; reset if needed to keep tests independent.

Summary

PER_CLASS lifecycle creates one test instance for all tests in a class.

This allows sharing state and setup between tests easily.

It can improve performance and simplify setup but requires careful state management.