skip to content

@BeforeAll / @AfterAll

@BeforeAll and @AfterAll run once per class for expensive shared setup, and must be static unless you switch to PER_CLASS lifecycle. The static requirement and its escape hatch is the usual follow-up question.

part ofJavaoverview, primer and where to startread it →
on this pageshow

questions

5

What do @BeforeAll and @AfterAll do in JUnit 5, and how do they differ from @BeforeEach and @AfterEach?

level: juniorimportance: must knowfreq 70%

answer

  1. 'All' = once per class; 'Each' = once per test
  2. BeforeAll/AfterAll bracket the whole run
  3. BeforeEach/AfterEach bracket each test inside
  4. Expensive shared setup -> BeforeAll; fresh per-test state -> BeforeEach
  5. JUnit 4 equivalents: @BeforeClass/@AfterClass

basics

~10 s

@BeforeAll runs once before all the tests in a class; @AfterAll runs once after all of them. @BeforeEach and @AfterEach run before and after every single test method instead.

solid answer

~40 s

In JUnit 5, @BeforeAll marks a method that runs exactly once before any test in the class executes, and @AfterAll marks one that runs exactly once after all tests finish. They're for class-level setup and teardown of expensive, shared resources, e.g. starting a database or test server, then closing it. By contrast, @BeforeEach and @AfterEach run before and after each individual test method, so they fire N times for N tests and are meant to give each test a fresh, isolated state. A useful way to remember it: 'All' = once per class, 'Each' = once per test. Order is: @BeforeAll, then for every test (@BeforeEach, test, @AfterEach), then @AfterAll.

go deeper

for a junior

Can state that 'All' runs once per class and 'Each' runs once per test, and give an example use for each.

for a middle

Can describe the full execution order and choose the right hook based on cost vs isolation needs.

for a senior

Can articulate the isolation trade-off of sharing state via @BeforeAll and steer teams away from order-dependent tests.

for a principal

Frames lifecycle choices as a policy: when shared fixtures are acceptable, how they interact with parallelism, and the maintenance cost of cross-test coupling.

## The problem these annotations solve A **test class** is just a Java class containing **test methods** (methods marked `@Test`). When you run it, the testing framework (here **JUnit 5**, the standard Java unit-testing library) calls each test method and reports pass/fail. **Setup** is work you do *before* a test so it has what it needs (e.g. create an object, open a connection); **teardown** is cleanup done *after* (e.g. close that connection). JUnit gives you **lifecycle annotations** to attach such code to the right moment. ## The four lifecycle hooks - **`@BeforeEach`** — a method that runs **before every individual test method**. If a class has 5 tests, it runs 5 times. Use it to build fresh state so tests don't interfere. - **`@AfterEach`** — runs **after every individual test method** (5 times for 5 tests). Use it to clean up per-test state. - **`@BeforeAll`** — runs **exactly once, before the first test in the class** (not once per test). Use it for setup that is **expensive and safe to share** across all tests, e.g. starting an in-memory database, an embedded web server, or loading a large file. - **`@AfterAll`** — runs **exactly once, after the last test in the class** finishes. Use it to release whatever `@BeforeAll` acquired. ## Mental model: 'All' vs 'Each' `All` = the whole class, so **once**. `Each` = each test, so **N times**. That single distinction is the heart of the topic. ## Full execution order For a class with tests T1, T2: ``` @BeforeAll @BeforeEach -> T1 -> @AfterEach @BeforeEach -> T2 -> @AfterEach @AfterAll ``` So `@BeforeAll` and `@AfterAll` bracket the *entire* run; the `Each` hooks bracket *each* test inside that. ## Why not just put everything in @BeforeEach? You could, but re-doing expensive work (like spinning up a database) before every single test wastes time. `@BeforeAll` does it **once** and shares the result. The trade-off is **isolation**: anything shared via `@BeforeAll` is reused, so tests must not corrupt it. Per-test mutable state still belongs in `@BeforeEach`. ## A subtlety you must know Under JUnit 5's **default lifecycle**, `@BeforeAll`/`@AfterAll` methods **must be `static`** (because no test instance exists yet when they run). That's covered in depth in a separate question; just remember it pairs with these two annotations. ## JUnit 4 note If you've seen JUnit 4, the equivalents are `@BeforeClass`/`@AfterClass` (also static) and `@Before`/`@After`. JUnit 5 renamed them to the clearer `*All`/`*Each` names.

  • If a test mutates an object created in @BeforeAll, will later tests see the change?
    Yes. @BeforeAll runs once and the object is shared, so mutations persist across tests in that class — a common source of order-dependent flakiness. Put mutable per-test state in @BeforeEach instead.
  • What are the JUnit 4 names for these hooks?
    @BeforeClass/@AfterClass correspond to @BeforeAll/@AfterAll, and @Before/@After correspond to @BeforeEach/@AfterEach.

saying these in an interview costs you the question

  • Saying @BeforeAll runs before each test (that's @BeforeEach)
  • Thinking @BeforeAll re-runs per test method
  • Confusing JUnit 4 @Before with JUnit 5 @BeforeAll
  • Claiming @AfterAll runs even per test

context

open as a page

How do you decide whether a piece of setup belongs in @BeforeAll or @BeforeEach? What's the trade-off?

level: middleimportance: must knowfreq 60%

basics

~20 s

Put setup in @BeforeAll if it's expensive and the same for every test and safe to share (it runs once). Put it in @BeforeEach if each test needs its own fresh copy (it runs every time). The trade-off is speed (BeforeAll) versus isolation (BeforeEach).

open as a page

Why must @BeforeAll and @AfterAll methods be static under JUnit 5's default lifecycle?

level: middleimportance: must knowfreq 65%

basics

~20 s

By default JUnit 5 creates a new instance of the test class for every test method. @BeforeAll/@AfterAll run once, before any instance exists, so they can't belong to an instance — they must be static (belong to the class itself).

open as a page

How would you use @BeforeAll and @AfterAll to manage an expensive shared resource like a test container or embedded server, and what should you watch out for?

level: seniorimportance: should knowfreq 55%

basics

~20 s

Start the expensive resource (e.g. a database container) once in @BeforeAll and stop it once in @AfterAll, so all tests in the class reuse it instead of paying the startup cost each time. Make sure each test cleans up its own data so tests stay independent.

open as a page

When a test class inherits from a base class with its own @BeforeAll, and there are multiple @BeforeAll methods, in what order does JUnit 5 run them — and how does @AfterAll mirror that?

level: principalimportance: nice to knowfreq 30%

basics

~20 s

Inherited @BeforeAll methods from a superclass run before the subclass's @BeforeAll; @AfterAll runs in the reverse order (subclass first, then superclass). Multiple @BeforeAll methods in the same class run in an unspecified order unless you set one with @Order.

open as a page