How do you tell Gradle to run your tests with JUnit 5 (Jupiter) instead of JUnit 4? What single line is involved and where does it go?
answer
- useJUnitPlatform() = JUnit 5
- default is JUnit 4
- on the Test task
- zero tests run = forgot it
- needs junit-platform-launcher runtime
basics
~10 sCall useJUnitPlatform() on the Test task in build.gradle.kts, e.g. tasks.test { useJUnitPlatform() }. Without it Gradle defaults to the JUnit 4 (Vintage) runner and won't discover Jupiter tests.
solid answer
~30 sGradle's `Test` task needs to know which **test framework** to drive. By default it uses JUnit 4. To run JUnit 5 you call `useJUnitPlatform()` on the test task: ```kotlin tasks.named<Test>("test") { useJUnitPlatform() } ``` That switches the task to the **JUnit Platform** launcher, which discovers and runs Jupiter (`@Test` from `org.junit.jupiter.api`) tests, plus any other Platform engine on the classpath. You also need the dependencies: `testImplementation("org.junit.jupiter:junit-jupiter")` and, on Gradle, the `junit-platform-launcher` runtime. If you forget `useJUnitPlatform()`, Gradle silently runs zero Jupiter tests because it's still looking for JUnit 4 style tests, which is a classic 'BUILD SUCCESSFUL but nothing ran' trap.
code
kotlin · 3 linestasks.named<Test>("test") {
useJUnitPlatform()
}go deeper
Know the one line: tasks.test { useJUnitPlatform() } enables JUnit 5, and that it goes on the Test task.
Explain that the default is JUnit 4, the platform-launcher runtime dependency, and the silent zero-tests trap.
Distinguish Platform vs engines (Jupiter/Vintage), explain last-call-wins, and how to verify via the test report and HTML output.
Standardize the selector across a multi-module build via a convention plugin so every module activates the Platform consistently and nobody hits the zero-tests trap.
## The problem this solves Gradle's built-in `Test` task type doesn't hard-code a test framework. It supports three: **JUnit 4**, the **JUnit Platform** (JUnit 5 / Jupiter and friends), and **TestNG**. You select one per `Test` task via a method call inside the task configuration. ## The three selector methods - `useJUnit()` — JUnit 4 (the legacy `junit:junit:4.x` engine). This is the historical default. - `useJUnitPlatform()` — the JUnit 5 **Platform** launcher. This is what runs Jupiter tests and is the modern default choice. - `useTestNG()` — the TestNG framework. Calling one of these is mutually exclusive: the **last call wins** for a given task. ## Why JUnit 5 is special JUnit 5 is not one library — it's the **Platform** (the launcher/discovery layer), plus **engines** that plug into it (Jupiter for JUnit 5 tests, Vintage for running old JUnit 4 tests on the Platform). `useJUnitPlatform()` activates the Platform launcher; whichever engines are on the test runtime classpath then get used. ## Wiring it up ```kotlin dependencies { testImplementation("org.junit.jupiter:junit-jupiter:5.10.2") testRuntimeOnly("org.junit.platform:junit-platform-launcher") } tasks.named<Test>("test") { useJUnitPlatform() } ``` The `junit-platform-launcher` runtime dependency became required explicitly in newer Gradle versions because Gradle stopped bundling it automatically. ## The silent-failure trap If you add Jupiter tests but **forget** `useJUnitPlatform()`, the task still runs with the JUnit 4 framework. JUnit 4 can't discover `org.junit.jupiter.api.Test` methods, so the build reports `BUILD SUCCESSFUL` having executed **zero** tests. Always confirm the test report shows the expected count.
- You added JUnit 5 tests and useJUnitPlatform(), but the build reports zero tests. What's a likely cause besides forgetting the selector?Missing the junit-platform-launcher on the test runtime classpath, or the tests use the wrong @Test annotation (org.junit.Test from JUnit 4 instead of org.junit.jupiter.api.Test), so Jupiter doesn't discover them.
- If you call both useJUnit() and useJUnitPlatform() in the same task block, what happens?No error — the last call wins. The task runs with whichever framework was selected last, which is a subtle source of confusion.
saying these in an interview costs you the question
- Saying JUnit 5 is the default in Gradle — JUnit 4 is the historical default; you must opt in.
- Claiming useJUnitPlatform() is a dependency rather than a Test-task method call.