Hibernate query caching types
In my Spring MVC application which retrieves objects from database, I need to cache my queries with the following criteria:
1) there will be five objects which should be persistent in cache and no select should be done in the database when accessing it during application lifetime.
2) each query should be cached for the 2 seconds.
I'm trying to solve it the following way:
declaring the following ehcache.xml
<ehcache>
<diskStore path="java.io.tmpdir"/>
<defaultCache maxElementsInMemory="10000"
eternal="false"
timeToIdleSeconds="120"
timeToLiveSeconds="120"
overflowToDisk="false"/>
<cache name="hibernate.test.org.hibernate.cache.UpdateTimestampsCache"
maxElementsInMemory="10000"
eternal="false"
timeToIdleSeconds="120"
timeToLiveSeconds="120"
overflowToDisk="true"/>
<cache name="hibernate.test.org.hibernate.cache.StandardQueryCache"
maxElementsInMemory="10000"
eternal="false"
timeToIdleSeconds="120"
timeToLiveSeconds="120"
overflowToDisk="true"/>
<cache name="com.doolloop.objects.Scene"
maxElementsInMemory="300"
eternal="false"
overflowToDisk="false"
timeToIdleSeconds="5"
timeToLiveSeconds="5"
/>
<cache name="query.homePageScene"
maxElementsInMemory="5"
eternal="true"
overflowToDisk="true"/>
</ehcache>
In my servlet xml I have the following enabled:
<prop key="hibernate.cache.use_second_level_cache">true</prop>
<prop key="hibernate.cache.use_query_cache">true</prop>
<prop key="hibernate.cache.provider_class">net.sf.ehcache.hibernate.SingletonEhCacheProvider</prop>
<prop key="hibernate.cache.provider_configuration_file_resource_path">/ehcache.xml</prop>
my mapping looks like this:
<class
name="com.doolloop.objects.Scene" table="scene"
>
<cache usage="read-only" region="query.homePageScene" />
<id name="id"
column="Id"
type="java.lang.Long" unsaved-value="null">
<generator class="sequence">
<param name="sequence">doolloop2.sceneseq</param>
</generator>
</id>
and now to methods:
one for retrieve one of the five pesistant queried object:
@Transactional(readOnly = true)
public Scene getHomePageScene(Long id) {
Session session = this.sessionFactory.getCurrentSession();
Query q = session.createQuery("select scene from com.doolloop.objects.Scene scene where scene.id=:id");
q.setLong("id",id);
q.setCacheable(true);
q.setCacheRegion("query.homePageScene");
Scene scene = (Scene)q.uniqueResult();
return scene;
}
and the second is for retrieving all other scenes:
@Transactional(readOnly = true)
public Scene getScene(Long id) {
Session session = this.sessionFactory.getCurrentSession();
开发者_如何学Go Query q = session.createQuery("select scene from com.doolloop.objects.Scene scene where scene.id=:id");
q.setLong("id",id);
Scene scene = (Scene)q.uniqueResult();
return scene;
}
My problem is that al my queries re always cached in query.homePageScene region no matter which method is executed.
What am I doing wrong?
Which version of Hibernate are you using? Are they part of the same session? If so, there's a bug in some versions of Hibernate that prevents the query cache from working if you are still in the same session that created the query cache. Also, try to enable some logging (DEBUG level for the org.hibernate.cache, IIRC). It says exactly what's going on.
You can also see these two JIRAs (they are the same issue, just in different JIRAs) for insights on how to do it properly. It can also serve to show you if your Hibernate version is affected by the bug.
https://issues.jboss.org/browse/JBPAPP-4224
http://opensource.atlassian.com/projects/hibernate/browse/HHH-5210
精彩评论