正如大多数持久层框架一样,MyBatis 同样提供了一级缓存和二级缓存的支持。

MyBatis 的缓存分为一级缓存和二级缓存,两种缓存的缓存粒度是一样的,都是对应一条 sql 查询语句,但是二者的生命周期是不一样的,一级缓存的生命周期是 SqlSession 对象的使用期间,随着 SqlSession 对象的死亡而消失;二级缓存如果没有更新数据的话,最长可以和应用的生命周期一样长。

首先查询二级缓存,然后再查询一级缓存。

一级缓存

一级缓存也叫本地缓存,在 MyBatis 中,一级缓存是在会话(SqlSession)层面实现的,这就说明一级缓存作用范围只能在同一个 SqlSession 中,跨 SqlSession 是无效的。当 Session flush 或 close 之后,该 Session 中的所有 Cache 就将清空。
MyBatis 中一级缓存是默认开启的,不需要任何配置。

这里我加一点我的个人理解(纯个人理解有争议我们可以讨论)MyBatis 的一级缓存存在的基础条件或者说理论依据是 MySql 的默认的事物隔离级别是可重复读,在同一个事务里面不管怎么读结果都是一样的,因此可以缓存。如果不是可重复读的话,而是和别的数据库一样是读已提交,那么这个缓存可能就会出问题。当然你也可以换种角度理解我这个观点,也就是数据库的隔离界别如果不是可重复读,那么使用 MyBatis 的一级缓存就会变成可重复的的效果,会出现问题。

二级缓存

二级缓存需要手动开启。

开启二级缓存以后,会被多个 SqlSession 共享,所以它是一个全局缓存。因此它的查询流程是先查二级缓存,再查一级缓存,最后再查数据库。

二级缓存相对于一级缓存来说,实现了 SqlSession 之间缓存数据的共享,同时缓存粒度也能够到 namespace 级别,并且还可以通过 Cache 接口实现类不同的组合,对 Cache 的可控性也更强。