10-Hibernate3.6.2 缓存
session = HibernateUtil.getSession(); Users users = (Users) session.get(Users.class, id); System.out.println(users.getBirthday()); Users users2 = (Users) session.get(Users.class, id); System.out.println(users.getName());
该程序当第一次查询Users对象时,hibernate会先到一级缓存中查找缓存中是否有该实体,如果有,就直接拿,否则就到数据库中去读取。这里缓存中没有,所以hibernate会到数据库中去读取数据。这里产生一条SQL语句。同时hibernate会将该实体对象放入到一级缓存中去。当第二次还查询该实体对象的时候,hibernate同样会先到一级缓存中去读,结果一级缓存中存在该实体对象,所以直接拿。故上面的程序实例只会产生一条SQL语句。
1、在hibernate.cfg.xml中开启二级缓存
<property name="cache.use_second_level_cache">true</property>
2、设置二级缓存的实现类
<property name="cache.provider_class">org.hibernate.cache.EHCacheProvider</property>
?Hibernate3所支持的缓存实现(具体可以看官方文档):
?
3、复制二级缓存的JAR包。
4、将缓存实现所需要的配置文件添加到系统的类加载路径中。对于EHCache缓存而言,它需要一个ehcache.xml配置文件。配置文件代码如下:
<ehcache> <defaultCache maxElementsInMemory="10000" eternal="false" timeToIdleSeconds="120" timeToLiveSeconds="120" overflowToDisk="true" /> </ehcache>
?????????? 5、设置对那些实体类。实体的那些集合属性开启二级缓存。在这里一般有如下两种方法:
<hibernate-mapping package="com.hibernate.domain"><class name="Users"><cache usage="read-only"/> <!-- 缓存策略为只读 --><id name="id"><generator /></id><property name="birthday" /><!-- 映射组件元素 --><component name="name"><!-- 映射组件的name属性指向包含实体 --><property name="firstName" column="first_name"/><property name="lastName" column="last_name"/></component></class></hibernate-mapping>
??????????????2)、在hibernate.cfg.xml文件中使用<class-cache.../>或者<collection-cache.../>元素对知道那个的持久化类、集合属性启用二级缓存
<class-cache usage="read-only" title="酷" border="0" alt="十-Hibernate3.6.2 缓存">6、测试public void query(int id){Session session = null;try {session = HibernateUtil.getSession();Users users = (Users) session.get(Users.class, id);System.out.println(users.getBirthday());} finally{if(session!=null) session.close();}try {session = HibernateUtil.getSession();Users users = (Users) session.get(Users.class, id);System.out.println(users.getName());}finally{if(session!=null) session.close();}}?当第一次查询Users实体之后,SessionFactory会将该实体缓存在二级缓存中,在这里先关闭session1然后重新创建session,在一次查询Users实体时,程序就可以直接使用缓存中已经存在的Users实体了。这里只产生一条SQL查询语句。
?
sessionFactory.evict(Users.class, id); //清除指定id的Users对象sessionFactory.evict(Users.class); // 清除所有的Users对象sessionFactory.evictCollection("Users.name",id); //清除指定id的Users所关联集合属性sessionFactory.evictCollection("Users.name"); //清除所有Users所关联集合属性
?
?CacheMode.NORMAL - 从二级缓存中读、写数据。
CacheMode.GET - 从二级缓存中读取数据,仅在数据更新时对二级缓存写数据。
CacheMode.PUT - 仅向二级缓存写数据,但不从二级缓存中读数据。
????????? CacheMode.REFRESH - 仅向二级缓存写数据,但不从二级缓存中读数据。通过 hibernate.cache.use_minimal_puts的设置,强制二级缓存从数据库中读取数据,刷新缓存内容。
?
<property name="generate_statistics">true</property><property name="cache.use_structured_entries">true</property>
?
Map cacheEntries = HibernateUtil.getSessionFactory().getStatistics() .getSecondLevelCacheStatistics("com.hibernate.domain.Users").getEntries();System.out.println(cacheEntries);
?
<property name="cache.use_query_cache">true</property>
?
public void cacheQuery(){Session session = HibernateUtil.getSession();List list = session.createQuery("from User u where u.id=:id") .setInteger("id", 2) .setCacheable(true) .setCacheRegion("name") .list();}
?
?
?
?