Сценарий тестирования Junit не выполняет откат - PullRequest
1 голос
/ 04 августа 2020

У меня есть следующий тест, в котором мне нужно показать, что моя транзакция работает и может выполнять откат. Проблема здесь в том, что мое исключение RuntimeException выполняется до того, как данные будут введены в базу данных. Так что отката не происходит. Как мне настроить этот тест?

@Test
@Rollback(true)
public void testForTransactionRollback() throws ClassNotFoundException, SQLException {

    User user = new User();
    user.setFirstName("Ivan");
    user.setLastName("Ivanov");
    user.setPhoneNumber("18000000");
    user.setEmail("mail@gmail.com");
    user.setCardNumber("4111111111111111");
    user.setDeliveryAddress("address");
    user.setComment("comment");

    String result = "";

    final ClientDAO clientDao1 = Mockito.spy(new ClientDAOImpl());

    final ClientDAOImpl clientDaoImpl = (ClientDAOImpl) clientDao1;

    Mockito.when(clientDao1.insert(user)).thenThrow(new RuntimeException());

    try {
        clientDao1.insert(user);
    } catch (final RuntimeException e) {
        System.out.println("Expected failure to trigger transaction caught");
    } finally {
        user = clientDao1.get(1L);
        if (user != null) {
            result = user.getFirstName();
        }
    }
    Assert.assertEquals("it should be equal", "", result);
}

1 Ответ

1 голос
/ 05 августа 2020

Я думаю, что проблема, с которой вы столкнулись, вызвана двумя внутренними транзакциями (одна внутри другой): первая находится внутри clientDao1.insert(user), а вторая - внутри вашего теста (при условии, что вы аннотировали свой тестовый класс с помощью @Transactional или @DataJpaTest, но вы этого не показали). Если RuntimeException выбрасывается во внутренней транзакции, что имеет место из-за

Mockito.when(clientDao1.insert(user)).thenThrow(new RuntimeException());

, это означает, что ваш внутренний clientDao1.insert метод не может восстановиться после этого исключения, а внешний метод (тестовый) не имеет ничего общего с скажем.

Вот почему данные НИКОГДА не будут записываться в базу данных или даже сохраняться (кэширование гибернации, конечно, если вы используете спящий режим в качестве поставщика JPA).

...