Мы уже давно используем подобный шаблон, чтобы обеспечить выполнение определенной операции с помощью BATCH NOWAIT
из соображений производительности.
try {
session.createSQLQuery("ALTER SESSION SET COMMIT_LOGGING='BATCH' COMMIT_WAIT='NOWAIT'").executeUpdate();
// Do the operation (which also calls transaction.commit())
return callback.apply(session);
} finally {
session.createSQLQuery("ALTER SESSION SET COMMIT_LOGGING='IMMEDIATE' COMMIT_WAIT='WAIT'").executeUpdate();
}
Это отлично работало в Hibernate 4. Что касается Hibernate 5, последний оператор терпит неудачу, потому что он не находится внутри транзакции (поскольку он только что был зафиксирован).
javax.persistence.TransactionRequiredException: выполнение запроса на обновление/удаление
Это не обновление и не удаление, но executeUpdate()
— единственный метод, который вы можете вызвать для выполнения этого оператора без возврата каких-либо строк. Это не должно быть в транзакции, поскольку переменные сеанса применяются ко всему соединению, и его необходимо выполнить для восстановления переменных сеанса, поскольку используется пул соединений.
Вместо этого я попытался использовать один из методов запроса, но в этом операторе есть строки -1, и он не позволяет мне складывать SELECT 1 FROM DUAL
в конце.
Есть ли способ выполнить собственный запрос из Hibernate, который не обновляет/удаляет и не возвращает результаты вне транзакции?