说一说 Mybatis 里面的缓存机制?

78 阅读2分钟

MyBatis 提供了一级缓存和二级缓存机制,用于提高数据查询性能。

一级缓存

作用范围一级缓存是 SqlSession 级别的缓存。在同一个 SqlSession 中,当执行相同的 SQL 查询时,MyBatis 会直接从缓存中获取数据,而不会再次执行 SQL 到数据库查询。

工作原理MyBatis 在执行查询语句时,会先创建一个 CacheKey 对象,该对象由 SQL 语句、输入参数等信息生成,作为缓存的键。然后在一级缓存(本质是一个 Map 结构,在 BaseExecutor 类中维护)中根据 CacheKey 查找对应的结果,如果找到则直接返回缓存结果;如果未找到,则执行 SQL 查询数据库,将查询结果存入一级缓存后再返回 。当 SqlSession 执行增、删、改操作(insert、update、delete )时,MyBatis 会清空一级缓存,以保证缓存数据的一致性

二级缓存

作用范围二级缓存是 namespace 级别的缓存,即同一个 Mapper 映射文件(对应一个 namespace )中的查询结果会被缓存。不同的 Mapper 的缓存相互隔离。

开启方式需要在 MyBatis 的配置文件中开启二级缓存( <setting name="cacheEnabled" value="true"/> ),并且在 Mapper 映射文件中通过 <cache> 标签配置缓存相关属性,如 eviction(缓存回收策略,如 LRU - 最近最少使用)、flushInterval(刷新间隔时间)、size(缓存最大容量)等。

工作原理当开启二级缓存后,MyBatis 在执行查询时,首先会查找二级缓存。如果在二级缓存中找到对应的数据,则直接返回;如果未找到,再去查找一级缓存,若一级缓存也没有,则执行 SQL 查询数据库,查询结果会先存入一级缓存,然后在 SqlSession 关闭时,将一级缓存中的数据存入二级缓存 。同样,当执行增、删、改操作时,会清空对应 namespace 的二级缓存。此外,MyBatis 还支持自定义缓存实现,开发者可以实现 org.apache.ibatis.cache.Cache 接口来自定义缓存逻辑。