Upgrade to Pro — share decks privately, control downloads, hide ads and more …

News from JUnit 5.x: From Revolution to Continuous Evolution

News from JUnit 5.x: From Revolution to Continuous Evolution

2017 marked a revolutionary year for the most popular Java testing framework: after two years of development, JUnit 5 was finally released - the first major release in over a decade. But work hasn't stopped since then. If anything, the amount of feedback and the number of feature requests from the community have increased considerably. As a consequence, there have been 4 new 5.x releases with additional features and enhancements, and the JUnit team is committed to keeping up the pace and shipping a new 5.x release every few months. So it's fair to say that JUnit is back to evolutionary releases, but the team intends to deliver them far more frequently than in the past.

In this session, we'll take a closer look at the new features such as improved Kotlin support, module path scanning, programmatic extension registration, tag expressions, annotation-based conditional test execution, improved parameterized tests and, last but not least, parallel test execution. Moreover, we'll see how the most popular Java build systems (Maven, Gradle, Ant) now provide built-in first-class support for running tests on the JUnit Platform. To round off the session, we will look at the roadmap of what's still to come.

Marc Philipp

March 19, 2019
Tweet

More Decks by Marc Philipp

Other Decks in Programming

Transcript

  1. 5
    NEWS FROM JUNIT 5
    FROM REVOLUTION TO CONTINUOUS
    EVOLUTION

    View Slide

  2. 5
    MARC PHILIPP
    So ware Engineer at
    JUnit commi er since 2012
    team lead since 2016
    Twi er:
    Web:
    @marcphilipp
    marcphilipp.de

    View Slide

  3. 5

    SHOW OF HANDS

    View Slide

  4. 5
    JUNIT 5 RELEASES
    5.0 – September 10, 2017
    5.1 – February 18, 2018
    5.2 – April 29, 2018
    5.3 – September 11, 2018
    5.4 – February 7, 2019

    View Slide

  5. 5
    AGENDA
    1. How to write tests and extensions using JUnit 5?
    2. What is the JUnit Pla orm and why do we need it?
    3. What’s s ll to come and how to get started?

    View Slide

  6. 5
    JUNIT JUPITER
    JUNIT JUPITER
    JUNIT JUPITER
    JUNIT JUPITER
    JUNIT JUPITER
    THE NEW TESTING FRAMEWORK FOR JAVA
    THE NEW TESTING FRAMEWORK FOR JAVA
    THE NEW TESTING FRAMEWORK FOR JAVA
    THE NEW TESTING FRAMEWORK FOR JAVA
    THE NEW TESTING FRAMEWORK FOR JAVA
    Image: NASA

    View Slide

  7. 5
    JUPITER?
    Nope, it’s just a new name so we can easily dis nguish it
    from the old JUnit and the other parts of JUnit 5.
    … and it’s the fi h planet from the sun.
    Is wri ng tests rocket science now?

    View Slide

  8. 5
    BASICS (DEMO)
    h ps:/
    /github.com/marcphilipp/junit5‑
    demo/tree/20190319‑javaland

    View Slide

  9. 5
    BASICS (RECAP)
    @Test is s ll a thing, but in org.junit.jupiter.api
    @Disabled instead of @Ignore
    @BeforeAll , @BeforeEach , @AfterEach , @AfterAll
    have new names
    Assertions look similar – a few new ones like
    assertThrows , assertAll
    Custom @DisplayNames to ease camel‑case fa gue
    @TestInstance(PER_METHOD or PER_CLASS)
    @Tag instead of @Category

    View Slide

  10. 5
    KOTLIN SUPPORT 5.1
    import org.junit.jupiter.api.*
    class KotlinAssertionsDemo {
    @Test
    fun `expected exception testing`() {
    val exception = assertThrows {
    Calculator().divide(1, 0)
    }
    assertEquals("/ by zero", exception.message)
    }
    @Test
    fun `grouped assertions`() {
    assertAll("Person properties",
    { assertEquals("Jane", person.firstName) },
    { assertEquals("Doe", person.lastName) }
    )
    }
    }

    View Slide

  11. 5
    DISPLAY NAME GENERATORS 5.4
    @DisplayNameGeneration(ReplaceUnderscores.class)
    class A_year_is_not_supported {
    @Test
    void if_it_is_zero() {/*...*/}
    @ParameterizedTest
    @ValueSource(ints = { -1, -4 })
    void if_it_is_negative(int year) {/*...*/}
    }

    View Slide

  12. 5
    MORE WAYS TO TEST (DEMO)
    h ps:/
    /github.com/marcphilipp/junit5‑
    demo/tree/20190319‑javaland

    View Slide

  13. 5
    MORE WAYS TO TEST (RECAP)
    @ParameterizedTest with different @Source
    annota ons
    @ValueSource , @EnumSource , @CsvSource ,
    @CsvFileSource , @MethodSource , @NullSource 5.4 ,
    @EmptySource 5.4 ,
    @ArgumentsSource(MyProvider.class) ,
    @YourCustomSource
    @RepeatedTest for flaky tests
    @TestFactory to produce dynamic tests

    View Slide

  14. 5
    PARALLEL EXECUTION 5.3 (DEMO)
    h ps:/
    /github.com/marcphilipp/junit5‑
    demo/tree/20190319‑javaland

    View Slide

  15. 5
    PARALLEL EXECUTION 5.3 (RECAP)
    Tests are run sequen ally by default
    Opt‑in and configure parallel execu on via configura on
    parameters
    @Execution(SAME_THREAD or CONCURRENT)
    Use @ResourceLock as declara ve synchroniza on
    mechanism

    View Slide

  16. 5
    TEST METHOD ORDERING 5.4
    @TestMethodOrder(Random.class) to ensure tests don’t
    rely on any order
    @TestMethodOrder(Alphanumeric.class) and
    @TestMethodOrder(OrderAnnotation.class) for
    integra on tests, changes execu on mode to
    SAME_THREAD by default
    Extensible: implement MethodOrderer

    View Slide

  17. 5
    EXTENSIONS (DEMO)
    h ps:/
    /github.com/marcphilipp/junit5‑
    demo/tree/20190319‑javaland

    View Slide

  18. 5
    EXTENSIONS (RECAP)
    Registra on (as many as you need):
    Declara ve: @ExtendWith on classes or methods
    Programma c: @RegisterExtension on fields 5.1
    Global: Via ServiceLoader (see )
    Implementa on:
    Extension marker interface
    one extension – n extension points/interfaces
    Built‑in @TempDir support 5.4
    User Guide

    View Slide

  19. 5
    COMPOSED ANNOTATIONS
    Use Jupiter annota ons as meta‑annota ons to create your
    own annota ons.
    @Retention(RUNTIME)
    @Target(METHOD)
    @ExtendWith(ConferenceExecutionCondition.class)
    @Tag("example")
    public @interface DisabledOnConference {}

    View Slide

  20. 5
    BUILT‑IN CONDITIONS 5.1
    @EnabledOnOs / @DisabledOnOs({LINUX, MAC, …})
    @EnabledOnJre / @DisabledOnJre({JAVA_11, …})
    @Enabled / DisabledIfSystemProperty(named =
    "someKey", matches = "someValue")
    @Enabled / DisabledIfEnvironmentVariable(named =
    "SOME_KEY", matches = "SOME_VALUE")
    @EnabledIf / @DisabledIf("Math.random() < 0.5")
    (experimental)

    View Slide

  21. 5
    EXTENSION POINTS
    Lifecycle: BeforeAllCallback , BeforeEachCallback ,
    BeforeTestExecutionCallback ,
    TestExecutionExceptionHandler ,
    AfterTestExecutionCallback , AfterEachCallback ,
    AfterAllCallback
    Other: ExecutionCondition , TestInstanceFactory 5.3
    , TestInstancePostProcessor , ParameterResolver ,
    TestWatcher 5.4 ,
    TestTemplateInvocationContextProvider

    View Slide

  22. 5
    THIRD‑PARTY EXTENSIONS
    JUnit Pioneer, Spring, Mockito, Testcontainers, Docker,
    Wiremock, JPA, Selenium/WebDriver, DbUnit, Ka a, Jersey,
    GreenMail, S3Mock, Citrus Framework, XWiki, …
    h ps:/
    /github.com/junit‑team/junit5/wiki/Third‑party‑
    Extensions

    View Slide

  23. 5
    AGENDA
    1. How to write tests and extensions using JUnit 5? ✅
    2. What is the JUnit Pla orm and why do we need it?
    3. What’s s ll to come and how to get started?

    View Slide

  24. 5
    JUNIT PLATFORM
    JUNIT PLATFORM
    JUNIT PLATFORM
    JUNIT PLATFORM
    JUNIT PLATFORM
    PLATFORM FOR TESTING ON THE JVM
    PLATFORM FOR TESTING ON THE JVM
    PLATFORM FOR TESTING ON THE JVM
    PLATFORM FOR TESTING ON THE JVM
    PLATFORM FOR TESTING ON THE JVM
    Image: NASA

    View Slide

  25. 5
    JUNIT AS A PLATFORM?
    JUnit has always been a pla orm
    for IDEs and build tools
    for other tes ng frameworks
    Closely coupled (internal APIs, reflec on, serializa on)

    View Slide

  26. 5
    COUPLING

    View Slide

  27. 5
    If JUnit is a pla orm, let’s design for it!

    View Slide

  28. 5
    SEPARATION OF CONCERNS
    1. An API to write tests and extensions (Jupiter API)
    2. Extensible mechanisms to discover and execute tests (Test
    Engine SPI)
    3. An API for test execu on by tools (Launcher API)

    View Slide

  29. 5
    DESIGN GOALS
    Flexibility: Adding new features should be easy. It should
    be clear whether a change might poten ally break a client.
    Backward Compa bility: Test wri en with JUnit 3 and 4
    should s ll run
    Forward Compa bility: Old IDEs and build tools should be
    able to execute new tests

    View Slide

  30. 5

    View Slide

  31. 5
    JUNIT 5
    =
    JUPITER + VINTAGE + PLATFORM

    View Slide

  32. 5
    COMPATIBILITY / MIGRATION
    Vintage Engine to run JUnit 3/4 tests on the Pla orm
    @Category(UI.class) maps to com.acme.UI tag
    Limited support for JUnit 4 Rules to ease migra on
    Migra on support for @Ignore 5.4
    IDEs provide tools to convert test classes to Jupiter API
    Community‑provided migra on tool:
    h ps:/
    /github.com/boyarsky/convert‑junit4‑to‑junit5

    View Slide

  33. 5
    BUILD TOOL SUPPORT
    Na ve support in Gradle (≥ 4.6), Ant (≥ 1.10.3), and Maven
    Surefire (≥ 2.22.0)
    ConsoleLauncher to run tests from the command line or
    to support other build tools (e.g. Bazel)

    View Slide

  34. 5
    IDE SUPPORT
    Excellent support
    IntelliJ IDEA (≥ 2016.2)
    Eclipse (≥ 4.7.1a)
    Visual Studio Code (Java Test Runner ≥ 0.4.0)
    Netbeans (≥ 10.0)
    For other tools, there’s @RunWith(JUnitPlatform)

    View Slide

  35. 5
    THIRD‑PARTY ENGINES
    Specsy, Spek, KotlinTest, Cucumber, Drools, jqwik, Brahms,
    Mainrunner, …
    h ps:/
    /github.com/junit‑team/junit5/wiki/Third‑party‑
    Extensions

    View Slide

  36. 5
    USING MULTIPLE ENGINES (DEMO)
    h ps:/
    /github.com/junit‑team/junit5‑
    samples/tree/master/junit5‑mul ple‑engines

    View Slide

  37. 5
    USING MULTIPLE ENGINES (RECAP)
    Mul ple test engines can be used in a single test run
    Dis nc on between testImplementation and
    testRuntimeOnly dependencies
    Allows to gradually migrate tests from one test engine to
    another (e.g. from Vintage to Jupiter)

    View Slide

  38. 5
    TAG EXPRESSIONS 5.1
    Precisely specify which tests to run based on tags:
    test {
    useJUnitPlatform {
    includeTags("(smoke & feature-a) | (!smoke & feature-b)")
    }
    }

    View Slide

  39. 5
    SUPPORT FOR JAVA MODULES 5.1
    Execute all tests in a module:
    Scan the module path:
    $ java -jar junit-platform-console-standalone-1.4.0.jar \
    --select-module com.acme.foo
    $ java -jar junit-platform-console-standalone-1.4.0.jar \
    --scan-modules

    View Slide

  40. 5
    AGENDA
    1. How to write tests and extensions using JUnit 5? ✅
    2. What is the JUnit Pla orm and why do we need it? ✅
    3. What’s s ll to come and how to get started?

    View Slide

  41. 5
    ROADMAP AND
    ROADMAP AND
    ROADMAP AND
    ROADMAP AND
    ROADMAP AND
    RESOURCES
    RESOURCES
    RESOURCES
    RESOURCES
    RESOURCES
    Image: NASA

    View Slide

  42. 5
    IMPORTANT FUTURE MILESTONES
    Execu ng tests in user‑defined threads/containers
    Global Timeouts
    New repor ng format that supports new features
    Declara ve Test Suites
    Parameterized Test Classes
    Scenario Tests
    Your ideas?

    View Slide

  43. 5
    GETTING STARTED
    User Guide:
    Sample projects for Ant, Bazel, Gradle, and Maven:
    Javadoc:
    h p:/
    /junit.org/junit5/docs/current/user‑guide/
    h ps:/
    /github.com/junit‑team/junit5‑samples
    h p:/
    /junit.org/junit5/docs/current/api/

    View Slide

  44. 5
    WANTED: FEEDBACK!
    StackOverflow:
    Code & Issues:
    Chat with the team:
    Twi er:
    h p:/
    /stackoverflow.com/ques ons/tagged/junit5
    h ps:/
    /github.com/junit‑team/junit5/
    h ps:/
    /gi er.im/junit‑team/junit5
    h ps:/
    /twi er.com/juni eam

    View Slide

  45. 5
    SUPPORT JUNIT
    Support the JUnit team with dona ons:
    h ps:/
    /junit.org/sponsoring

    View Slide

  46. 5
    EXAMPLE CODE
    Jupiter:
    Pla orm:
    h ps:/
    /github.com/marcphilipp/junit5‑
    demo/tree/20190319‑javaland
    h ps:/
    /github.com/junit‑team/junit5‑
    samples/tree/master/junit5‑mul ple‑engines

    View Slide

  47. 5
    QUESTIONS?
    Come talk to Chris an Stein ( ) and me at the
    booth a er this talk
    or
    ping / on Twi er
    @sormuras
    @marcphilipp @juni eam

    View Slide

  48. 5
    THANKS!

    View Slide