>>分享JPA、Hibernate、Mybatis对象持久化技术,对《精通JPA与Hibernate:Java对象持久化详解》提供技术支持 书籍支持  卫琴直播  品书摘要  在线测试  资源下载  联系我们
发表一个新主题 开启一个新投票 回复文章 您是本文章第 23359 个阅读者 刷新本主题
 * 贴子主题:  Hibernate的二级缓存 回复文章 点赞(0)  收藏  
作者:flybird    发表时间:2020-01-25 00:43:51     消息  查看  搜索  好友  邮件  复制  引用

一级缓存:

Hibernate默认是开启一级缓存的,一级缓存存放在session上,属于事务级数据缓冲。

二级缓存:

二级缓存是在SessionFactory,所有的Session共享同一个二级Cache。二级Cache的内部如何实现并不重要,重要的是采用哪种正确的缓存策略,以及采用哪个Cache提供器。

二级缓存也分为了两种:

内置缓存:Hibernate自带的,不可卸载,通常在Hibernate的初始化阶段,Hibernate会把映射元数据和提前定义的SQL语句放置到SessionFactory的缓存中。该内置缓存是仅仅是只读的。

外置缓存:通常说的二级缓存也就是外置缓存,在默认情况下SessionFactory不会启用这个缓存插件,外置缓存中的数据是数据库数据的复制,外置缓存的物理介质能够是内存或者硬盘。

点击在新窗口中浏览原图
CTRL+鼠标滚轮放大或缩小

二级缓存的配置

hibernate支持的缓存插件
点击在新窗口中浏览原图
CTRL+鼠标滚轮放大或缩小

适合存放到第二级缓存中?   
1) 很少被修改的数据   
2) 不是很重要的数据,允许出现偶尔并发的数据   
3) 不会被并发访问的数据   
4) 常量数据   

不适合存放到第二级缓存的数据?   
1) 经常被修改的数据   
2) 绝对不允许出现并发访问的数据,如财务数据,绝对不允许出现并发   
3) 与其他应用共享的数据。

1. 导入jar包和创建配置文件 ehcache.xml
Maven依赖

<!-- 二级缓存 EHcache -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-ehcache</artifactId>
<version>5.2.17.Final</version>
</dependency>

ehcache.xml

<?xml version="1.0" encoding="UTF-8"?>
<ehcache>
<diskStore path="d:/ehcache/"></diskStore>
<!-- 默认缓存配置 -->
<defaultCache
maxElementsInMemory="10000"
eternal="false"
timeToIdleSeconds="120"
timeToLiveSeconds="120"
overflowToDisk="true" />

</ehcache>

2. 在 hibernate.cfg.xml 中开启二级缓存

<!-- 配置二级缓存 ehCache  -->
  <property name="hibernate.cache.use_second_level_cache">true</property>
  <!-- 配置二级缓存技术提供者 -->
  <property name="hibernate.cache.region.factory_class">org.hibernate.cache.ehcache.EhCacheRegionFactory</property>
  
<!-- ORM 映射关系 -->
  <mapping resource="cn/jq/hibernate5/model/Teacher.hbm.xml"/>
  <mapping resource="cn/jq/hibernate5/model/Student.hbm.xml"/>
<!-- 配置二级缓存类  也可在xxx.hbm.xml 里配置二级缓存类 -->
  <class-cache usage="read-write" class="cn.jq.hibernate5.model.Student"/>
  <class-cache usage="read-write" class="cn.jq.hibernate5.model.Teacher"/>

3. 测试

@Test
public void test() {
Student student = session.get(Student.class, 2);
System.out.println(student);

transaction.commit();
session.close();

session = sessionFactory.openSession();
transaction = session.beginTransaction();
Student student2 = session.get(Student.class, 2);
System.out.println(student2);

}

session查询一次: session关闭后,不会发起sql查询, 在二级缓存中提取数据

Student [id=2, sname=学生2, teacher=Teacher [id=1, tname=老师1]]
Student [id=2, sname=学生2, teacher=Teacher [id=1, tname=老师1]]


HibernateUtil 工具类的封装

HibernateUtil :

//获取HIbernate与数据库的连接session会话对象, 此工具类采取单例模式
public class HibernateUtil {

private static HibernateUtil hibernateUtil = null;

private HibernateUtil() {}

public static HibernateUtil getInstance() {
if(hibernateUtil == null) {
hibernateUtil = new HibernateUtil();
}
return hibernateUtil;
}

public SessionFactory getSessionFactory() {
// 配置类: 封装有我们的配置文件里的配置信息, 返回的 configuration 包含有配置文件里的具体信息
Configuration configuration = new Configuration().configure();
// Hibernate5规定: 所有配置或服务要生效, 必须将其注册到一个服务注册类中
StandardServiceRegistry serviceRegistry = configuration.getStandardServiceRegistryBuilder().build();
//
SessionFactory sessionFactory = new MetadataSources(serviceRegistry).buildMetadata().buildSessionFactory();
return sessionFactory;
}

public Session getSession() {
//获取与当前线程绑定的session,同时,在核心配置文件中配置Session的管理方式为thread线程管理方式:
//<property name="current_session_context_class">thread</property>
return getSessionFactory().getCurrentSession();
}
}

<property name="current_session_context_class">thread</property>  

Dao:

public class StudentDao {
public void save(Student student) {
Session session = HibernateUtil.getInstance().getSession();

Transaction transaction = session.beginTransaction();
session.save(student);
transaction.commit();
//thread线程方式来管理session对象, 当事务提交时, Hibernate会自动关闭session,
System.out.println(session.isOpen()); //false
}
}

Test:

public class Test {
public static void main(String[] args) {
StudentService studentService = new StudentService();
Student student = new Student();
student.setSname("HibernteUtil 测试");

studentService.save(student);
}
}

-------
Hibernate:
    insert  into  t_student(sname, teacher_id)
    values (?, ?)
false






程序猿的技术大观园:www.javathinker.net

[这个贴子最后由 flybird 在 2020-02-23 12:08:59 重新编辑]
  Java面向对象编程-->流程控制
  JavaWeb开发-->JSP中使用JavaBean(Ⅰ)
  JSP与Hibernate开发-->持久化层的映射类型
  Java网络编程-->安全网络通信
  精通Spring-->绑定表单
  Vue3开发-->Vue CLI脚手架工具
  孙卫琴的Java对象持久化技术之旅-视频讲座
  孙卫琴的《精通JPA与Hibernate》的读书笔记:在程序中动态指定...
  JPA和事务管理
  推荐:Spring,JPA与Hibernate的最新整合范例讲解(孙卫琴主讲...
  用注解和XML描述对象-关系映射的区别,和优缺点
  理解事务的四种隔离级别
  深入理解乐观锁和悲观锁
  JPA EntityManager类的常用方法的作用
  JPA/Hibernate:基于版本的乐观锁并发控制
  Hibernate的八种对象标识符生成策略
  JPQL与SQL的区别
  Hibernate 对象-关系映射: @注解与xml 配置方式比较
  JPA (Java Persistence API)2.2 的一些新特性
  hibernate 5的二级缓存案例讲解
  Hibernate解压包的目录结构
  更多...
 IPIP: 已设置保密
楼主      
1页 0条记录 当前第1
发表一个新主题 开启一个新投票 回复文章


中文版权所有: JavaThinker技术网站 Copyright 2016-2026 沪ICP备16029593号-2
荟萃Java程序员智慧的结晶,分享交流Java前沿技术。  联系我们
如有技术文章涉及侵权,请与本站管理员联系。