Исключение из ограничения уникальности не вызывается сразу в тестовом примере - PullRequest
0 голосов
/ 03 мая 2018

У меня есть тест junit, чтобы проверить, что мои ограничения уникальности работают правильно. Я обнаружил, что после добавления повторяющейся записи, чтобы получить ожидаемое исключение, мне нужно либо сделать запрос в БД, либо установить @Rollback (false) в тесте. (Полагаю, это связано с какой-то ленивой логикой коммита?)

Это ожидается? Или есть лучший способ написать этот тест?

@Test
@Rollback(false) // without this no duplicate is found.  Documentation and test1() don't accord with this. Why?
public void addDuplExchange() {
    exception.expect(DataIntegrityViolationException.class); //org.springframework.dao.DataIntegrityViolationException: could not execute statement; SQL [n/a]; constraint ["UK_CI07R484MKOOCNBAD6Q6HG1DB_INDEX_2 ON PUBLIC.EXCHANGES(EXCHANGE_NAME_LOWERCASE) VALUES ('exchange3', 1)"; SQL statement:

    System.out.println("add dupl exchange...");
    ExchangeDbo e3a1 = dbService.addNewExchange("Exchange3");
    System.out.println(e3a1);
    ExchangeDbo e3a2 = dbService.addNewExchange("eXcHanGe3"); // this should fail
    System.out.println(e3a2);
    //      List<ExchangeDbo> x = dbService.getAllExchanges();
    //      x.forEach(System.out::println);
}

1 Ответ

0 голосов
/ 03 мая 2018

Это ожидается?

Абсолютно.

Я предполагаю, что dbService.addNewExchange() вызывает repository.save() (что, в свою очередь, вызывает entityManager.persist() внутри страны). Это только делает только что созданный объект managed , что означает, что его состояние теперь будет отслеживаться JPA. Состояние этой сущности будет сброшено в db при необходимости, не позднее, чем при фиксации транзакции .

Мне нужно либо сделать запрос в БД, либо установить в тесте @Rollback (false)

По умолчанию Hibernate выполняет сброс при фиксации транзакции и перед запросами. Последнее должно гарантировать, что изменения, внесенные в сущности, отражены в результатах запроса.

Чтобы сделать тест неудачным, либо переключитесь на repository.saveAndFlush(), немедленно принудительно сбросив, либо явно сбросив контекст, введя EntityManager в тест и вызвав EntityManager.flush() после того, как оба вызова dbService.addNewExchange() были сделаны ,

...