Migrating to JUnit 5

Migrating to JUnit 5

by Joanna Hu at TWJUG 20201021 https://twjug.kktix.cc/events/twjug202010

2102a6b8760bd6f57f672805723dd83a?s=128

line_developers_tw

October 21, 2020
Tweet

Transcript

  1. 0LJUDWLQJWR -8QLW -RDQQD+X 

  2. About the Speaker Joanna Hu • Backend Engineer • Working

    in LINE Taiwan since 2019
  3. 01 02 03 Summary :KDWLV-8QLW :K\PLJUDWLQJWR-8QLW +RZWRPLJUDWHWR-8QLW

  4. :KDWLV-8QLW • -8QLW-XSLWHUWKHQHZSURJUDPPLQJH[WHQVLRQPRGHOIRUZULWLQJWHVWVDQGH[WHQVLRQVLQ-8QLW • -8QLW9LQWDJH 7HVW(QJLQH IRUUXQQLQJ-8QLWDQG-8QLWEDVHGWHVWVRQWKHSODWIRUP • -8QLW3ODWIRUP IRXQGDWLRQIRUODXQFKLQJWHVWLQJIUDPHZRUNVRQWKH-90

    ※Source from︓https://dzone.com/articles/7-reasons-to-consider-junit-5
  5. :K\PLJUDWLQJWR-8QLW • 6XSSRUWHGLQPDMRU,'(%XLOGWRROV • ,QWHOOLM ,'($(FOLSVH96&RGH • 0DYHQ*UDGOH • (DV\PLJUDWLRQ

    • -8QLWWHVWVFDQFRH[LVWZLWK-8QLWWHVWV • :HFDQXVHERWK-8QLW$VVHUW- DVVHUWLRQVLQRQHWHVW • 1HZ)HDWXUHV
  6. -8QLW1HZ)HDWXUHV • 1HVWHGWHVWV • 'LVSOD\QDPH • 3DUDPHWHUL]HGWHVWV • 0XOWLSOH5XQQHUV •

    %HWWHU$VVHUWLRQV EXWZHUHFRPPHQG$VVHUW- LQVWHDG
  7. 1HVWHGWHVWV • #1HVWHGFDQKDYHPXOWLSOHOHYHOV • 6XSSRUWQRQVWDWLFLQQHUFODVV class TestingAStackDemo { Stack<Object> stack;

    @Test void isInstantiatedWithNew() { new Stack<>(); } @Nested class WhenNew { @BeforeEach void createNewStack() { stack = new Stack<>(); } @Test void isEmpty() { assertTrue(stack.isEmpty()); } @Test void throwsExceptionWhenPopped() { assertThrows(EmptyStackException.class, stack::pop); } @Nested class AfterPushing { // more tests... } } }
  8. 1HVWHGWHVWV

  9. 'LVSOD\QDPHV • $GG#'LVSOD\1DPH DQQRWDWLRQ • 6XSSRUWDGGLQJRQFODVVPHWKRG @DisplayName("A stack") class TestingAStackDemo

    { Stack<Object> stack; @Test @DisplayName("is instantiated with new Stack()") void isInstantiatedWithNew() { new Stack<>(); } @Nested @DisplayName("when new") class WhenNew { @BeforeEach void createNewStack() { stack = new Stack<>(); } @Test @DisplayName("is empty") void isEmpty() { assertTrue(stack.isEmpty()); } @Nested @DisplayName("after pushing an element") class AfterPushing { // more tests... } } }
  10. 'LVSOD\QDPHV • $GG#'LVSOD\1DPH DQQRWDWLRQ • 6XSSRUWDGGLQJRQFODVVPHWKRG

  11. 3DUDPHWHUL]HGWHVWV -8QLW class CalculatorJUnit5Test { @ParameterizedTest @ValueSource(strings = { "",

    " ", " " }) void isBlank_ShouldReturnTrueForBlankStrings(String input) { assertThat(StringUtils.isBlank(input)).isTrue(); } @ParameterizedTest @NullSource void isBlank_ShouldReturnTrueForNullStrings(String input) { assertThat(StringUtils.isBlank(input)).isTrue(); } @ParameterizedTest @CsvSource({ "0,0,0", "1,1,2" }) void add(int first, int second, int expected) { final Calculator calculator = new Calculator(); final int result = calculator.add(first, second); assertThat(result).isEqualTo(expected); } }
  12. 0XOWLSOH5XQQHUV -8QLWRQO\VXSSRUWVVLQJOHUXQQHUZKLOH-8QLWVXSSRUWVPXOWLSOHH[WHQVLRQV // JUnit 4 @RunWith(MockitoJUnitRunner.class) public class CMSProductServiceTest {

    // ... } // JUnit 5 @ExtendWith({ MockitoExtension.class, SoftAssertionsExtension.class }) public class CMSProductServiceTest { // ... }
  13. +RZWRPLJUDWHWR-8QLW • 8SJUDGHWR-8QLWLQ0DYHQ*UDGOH • 8SJUDGH0DYHQWR 2U0DYHQVXUHILUHIDLOVDIHSOXJLQWR • 8SJUDGH*UDGOHWR • :ULWHQHZWHVWVLQ-8QLW

    • 0LJUDWHH[LVWLQJ-8QLWWHVWV • 5HZULWH-8QLW5XOHWR-8QLW([WHQVLRQ LIDQ\
  14. 0LJUDWHH[LVWLQJ-8QLWWHVWV JUnit 4 JUnit 5 org.junit.Test org.junit.jupiter.api.Test org.junit.Before org.junit.jupiter.api.BeforeEach org.junit.After

    org.junit.jupiter.api.AfterEach org.junit.BeforeClass org.junit.jupiter.api.BeforeAll org.junit.AfterClass org.junit.jupiter.api.AfterAll org.junit.Ignore org.junit.jupiter.api.Disabled org.junit.Assert org.junit.jupiter.api.Assertions (we use AssertJ) org.junit.Assert.assertThat org.hamcrest.MatcherAssert.assertThat org.junit.runner.RunWith org.junit.jupiter.api.extension.ExtendWith org.mockito.junit.MockitoJUnitRunner org.mockito.junit.jupiter.MockitoExtension org.springframework.test.context.junit4.SpringRu nner org.springframework.test.context.junit.jupiter.Spri ngExtension
  15. 5HZULWH-8QLW5XOHWR-8QLW([WHQVLRQ -8QLW5XOH public class EmbeddedMySqlRule extends ExternalResource { private EmbeddedMysql

    embeddedMysql; @Override protected void before() { // ... embeddedMysql = EmbeddedMysql.anEmbeddedMysql(config, downloadConfig) .addSchema("ecac", ScriptResolver.classPathScript("db/setup.sql")) .start(); } @Override protected void after() { if (embeddedMysql != null) { embeddedMysql.stop(); } } }
  16. 5HZULWH-8QLW5XOHWR-8QLW([WHQVLRQ -8QLW([WHQVLRQ public class EmbeddedMySqlExtension implements AfterAllCallback, BeforeAllCallback { private

    EmbeddedMysql embeddedMysql; @Override public void beforeAll(ExtensionContext extensionContext) throws Exception { // ... embeddedMysql = EmbeddedMysql.anEmbeddedMysql(config, downloadConfig) .addSchema("ecac", ScriptResolver.classPathScript("db/setup.sql")) .start(); } @Override public void afterAll(ExtensionContext extensionContext) throws Exception { if (embeddedMysql != null) { embeddedMysql.stop(); } } }
  17. 0LJUDWH8VLQJ,QWHOOL-,'($ 0LJUDWHRQHWHVW 0LJUDWHDOOWHVWV 5HIDFWRU!0LJUDWH https://blog.jetbrains.com/idea/2020/08/migrating-from-junit-4-to-junit-5/

  18. • -8QLWZHEVLWHhttps://junit.org/junit5/ • 5HDVRQVWR&RQVLGHU-8QLWhttps://dzone.com/articles/7-reasons-to-consider-junit-5 • 0LJUDWLQJIURP-8QLWWR-8QLWhttps://blog.jetbrains.com/idea/2020/08/migrating-from-junit-4-to-junit-5/ 5HIHUHQFHV

  19. THANK YOU