一、一级缓存(本地缓存)sqlSession级别的缓存,一级缓存是一直开启的;sqlSession级别的一个Map
与数据库同一次会话期间查询到的数据会放在本地缓存中;
以后如果需要相同的数据,可以直接从缓存中拿,不需要再查询数据库;
一级缓存失效的情况:
① 不同的sqlSession,缓存不同;
② 相同的sqlSession,但是查询数据不一样;
③ 相同的sqlSession,但是在两次一样的查询数据之间,有增删改操作,导致数据库数据有改变;
④ 相同的sqlSession,执行了清除缓存的操作,sqlSession.clearCache()
二、二级缓存(全局缓存)基于nameSpace级别的缓存,一个nameSpace对应一个二级缓存
1.工作机制:
一次会话,查询一条数据,这个数据会被放入一级缓存中;
当会话关闭,一级缓存会失效,这时候数据信息会放置二级缓存中;
开启新的会话,就可以利用二级缓存查询数据;
注意,不同的nameSpace查询出的数据会放在自己对于的map中
查出的数据默认会放入一级缓存中,只有会话提交或者关闭,数据才会从一级缓存转移到二级缓存中
2.使用
(1)开启全局二级缓存设置 <setting name="cacheEnabled" value="true">
(2)在mapper.xml中配置使用二级缓存使用<cache></cache>标签,参数介绍
① eviction=“FIFO”:缓存回收策略:默认的是 LRU。 LRU – 最近最少使用的:移除最长时间不被使用的对象。 FIFO – 先进先出:按对象进入缓存的顺序来移除它们。 SOFT – 软引用:移除基于垃圾回收器状态和软引用规则的对象。 WEAK – 弱引用:更积极地移除基于垃圾收集器状态和弱引用规则的对象。 ② flushInterval:刷新间隔,单位毫秒 默认情况是不设置,也就是没有刷新间隔,缓存仅仅调用语句时刷新 ③ size:引用数目,正整数 代表缓存最多可以存储多少个对象,太大容易导致内存溢出 ④ readOnly:只读,true/false true:只读缓存;会给所有调用者返回缓存对象的相同实例。因此这些对象不能被修改。这提供了很重要的性能优势。 false:读写缓存;会返回缓存对象的拷贝(通过序列化)。这会慢一些,但是安全,因此默认是 false。 (3)POJO需要实现序列化接口三、缓存相关的配置以及属性
1、全局setting的cacheEnable:配置二级缓存的开关。一级缓存一直是打开的。 2、select标签的useCache属性: 配置这个select是否使用二级缓存。一级缓存一直是使用的 3、sql标签的flushCache属性:增删改默认flushCache=true。sql执行以后,会同时清空一级和二级缓存。查询默认flushCache=false。 4、sqlSession.clearCache(): 只是用来清除一级缓存。 5、当在某一个作用域 (一级缓存Session/二级缓存Namespaces) 进行了 C/U/D 操作后,默认该作用域下所有 select 中的缓存将被clear。 四、缓存的原理