Ответ 1
Собственные запросы очищают записи кэша второго уровня.
- Собственные запросы (на самом деле это только для встроенных вставок/удалений/обновлений, а не для запросов) являются недействительными записи кэша второго уровня для всех кешей (WHOLE CACHE). Я проверил это с текущей стабильной версией Hibernate: 4.1.9. Это разумно, потому что Hiberante не может знать, что было изменено в БД, поэтому единственным вариантом является аннулирование всего кеша второго уровня. Это может быть серьезной проблемой в некоторых системах, которые в значительной степени зависят от кеша второго уровня.
Существует хотя бы возможность указать, что из кэша второго уровня должно быть недействительным (или даже указать, что ничего не выведено из кеша). Посмотрите на замечательный пост в блоге http://www.link-intersystems.com/bin/view/Blog/Hibernate%27s+second+level+cache+and+native+queries, где это объясняется полностью.
Чтобы предотвратить Hibernate от недействительности чего-либо из кеша:
SQLQuery sqlQuery = session.createSQLQuery("ALTER SESSION SET NLS_COMP = 'BINARY'");
sqlQuery.addSynchronizedQuerySpace("");
int updatedEntities = sqlQuery.executeUpdate();
Чтобы указать Hibernate сделать недействительным только кеш-объект Person:
SQLQuery sqlQuery = session.createSQLQuery("UPDATE PERSON SET ... WHERE ...");
sqlQuery.addSynchronizedEntityClass(Person.class);
int updatedEntities = sqlQuery.executeUpdate();
Ответ на форуме спячки, который составляет 7 лет, говорит, что HQL обновления также очищают кеш второго уровня. Но верно ли это?
- HQL делает недействительным только область кэша второго уровня, которая связана с сущностью, в которую вы вставляете некоторые вставки/обновления/удаления. Это имеет смысл, потому что Hibernate знает, на какие объекты влияет HQL, он может очистить только область кэша второго уровня для этого объекта.
Пример:
entityManager.createQuery("delete from Person p where p.id = 1").executeUpdate();
Это приведет к недействительности "только" кэша объектов Person.
Мне не известно о возможности предотвратить Hibernate от недействительности кеша второго уровня для конкретной сущности, когда дело доходит до HQL.