Spring @Transactional метод Обработка ошибок - PullRequest
0 голосов
/ 23 сентября 2018

Я использую транзакционный метод, используя аннотацию @Transactional.Я пытаюсь сохранить объект в базе данных с помощью метода save () JpaRepository.(что приведет к ошибке из-за ограничений на отношение к базе данных.)

Теперь, когда я отлаживал программу, я обнаружил, что исключение выдается в конце транзакционного метода, а не при вызове save метода,Это совершенно отличное поведение от нетранзакционного метода.

Может кто-нибудь объяснить, почему это так?Почему исключение выдается в конце транзакционного метода, а не когда оно действительно должно произойти.

Мой второй вопрос: когда метод транзакционный, генерируется исключение DataViolationException, а когда нетранзакционный, исключениевыброшено PSQLException (используется база данных Postgres).Почему это так?

Ниже приведен код

@Transactional
public ResponseType methodA(UserObject userObject) {
    //save call
    jpaRepoObject.save(userObject);
    //next call will fail due to relational constraints on database
    jpaRepoObject.save(userObject); //should throw PSQLException/DataViolationException

     return new ResponseType("success"); //Error thrown after this line.
}

Ответы [ 2 ]

0 голосов
/ 23 сентября 2018

Это особенность JPA, называемая транзакционной записью.Все вставки и обновления, выполняемые вашим кодом, сохраняются реализацией Jpa до сброса транзакции.Это позволяет реализации jpa переупорядочивать эти действия в любом порядке.

Очистка означает выполнение всех действий, которые были сохранены до сих пор экземпляром entityManager.Вы можете указать, что entityManager сбрасывается, или он будет автоматически сбрасываться, как только будет достигнута граница транзакции.

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

Вы всегда можете запустить sql внутри транзакции и зафиксировать или откатить позже.Flushing запускает sql, но не фиксирует.

0 голосов
/ 23 сентября 2018

save не сразу сбрасывает данные в базовую базу данных.Во-первых, сущности сохраняются в кэш первого уровня, и, когда наступает время сброса (в конце транзакции - как в вашем случае или когда выдается запрос), только тогда сущности сохраняются в базе данных.

Чтобы увидеть поведение, которое вы ожидаете, используйте saveAndFlush метод.

...