验证内置的2级缓存
Ehcache缓存的配置
01.引入需要的ehcache 和mybatis-ehcache 两个jar包
02.在mapper文件中增加 <cache type="org.mybatis.caches.ehcache.EhcacheCache"/> <!-- 配置Ehcache缓存 -->
org.mybatis.caches.ehcache.EhcacheCache就是在mybatis-ehcache这个jar包中
03.引入需要的ecache.xml文件 就在ecache.jar中
创建对应的dao
public interface StudentDao { /** * 验证mybatis2级缓存! */ Student selectStudentById(Integer sId); }
创建对应的mapper文件
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-Mapper.dtd"> <mapper namespace="cn.bdqn.dao.StudentDao"> <cache/> <!-- 配置2级缓存 --> <select id="selectStudentById" resultType="Student"> select sid,sname from student where sid=#{xxx} </select> </mapper>
实体类实现Serializable序列化接口
/** *学生对应的实体类 */ public class Student implements Serializable { private Integer sId; private String sName; public Integer getsId() { return sId; } public void setsId(Integer sId) { this.sId = sId; } public String getsName() { return sName; } public void setsName(String sName) { this.sName = sName; } public Student(Integer sId, String sName) { super(); this.sId = sId; this.sName = sName; } public Student() { super(); } @Override public String toString() { return "Student [sId=" + sId + ", sName=" + sName +"]"; } }
把log4j的配置文件中的显示改成
增加测试类代码
package cn.bdqn.test; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import org.apache.ibatis.session.SqlSession; import org.junit.After; import org.junit.Before; import org.junit.Test; import cn.bdqn.bean.Student; import cn.bdqn.dao.StudentDao; import cn.bdqn.util.SessionUtil; public class TeacherTest { StudentDao dao; SqlSession session; @Before public void before() { // 因为需要关闭session 需要把session提取出去 session = SessionUtil.getSession(); dao = session.getMapper(StudentDao.class); } @After public void after() { if (session != null) { session.close(); } } /** * 验证2级缓存 * * 开启内置2级缓存的步骤 * 01.实体类对象 要实现serializable 序列化接口 * 02.在mapper文件中 增加 <cache/>节点 */ @Test public void test1() { Student student = dao.selectStudentById(1); System.out.println(student); session.close(); //关闭了session 一级缓存中的数据肯定清空了 session = SessionUtil.getSession(); //再次获取session 查询数据 dao = session.getMapper(StudentDao.class); //这时候不会再有sql语句了 因为2级缓存中存在相同的查询(mapper文件中sql的id)和相同的sql语句 Student student2 = dao.selectStudentById(1); System.out.println(student2); } }
运行的结果:
验证增删改对2级缓存的影响
在dao中新增方法
public interface StudentDao { /** * 验证mybatis2级缓存! */ Student selectStudentById(Integer sId); /** * 验证增删改查对2级缓存的影响! */ void addStudent(Student student); }
在mapper文件中新增
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-Mapper.dtd"> <mapper namespace="cn.bdqn.dao.StudentDao"> <cache/> <!-- 配置2级缓存 --> <select id="selectStudentById" resultType="Student"> select sid,sname from student where sid=#{xxx} </select> <!-- 新增一个学生 验证对2级缓存的影响 标签中 增加 flushCache="false" 可以设置在新增数据的时候不刷新2级缓存 但是一级缓存不能配置 也就是 只要是一级缓存的增删改 都会刷新 --> <insert id="addStudent">
insert into student values(#{sId},#{sName}) <!--#{sId},#{sName} 对应的是实体类中的属性 -->
</insert>
</mapper>
在测试类中新增
/** * 验证增删改对2级缓存的影响 */ @Test public void test2() { Student student = dao.selectStudentById(1); System.out.println(student); session.close(); //关闭了session 一级缓存中的数据肯定清空了 session = SessionUtil.getSession(); //再次获取session 查询数据 dao = session.getMapper(StudentDao.class); //新增学生信息 看看对2级缓存的影响 dao.addStudent(new Student(66,"测试")); Student student2 = dao.selectStudentById(1); System.out.println(student2); }
得到的结果:
2级缓存的关闭
/** * 2级缓存的关闭 * 01.局部关闭 * 在mapper文件中修改 * <select id="selectStudentById" useCache="false" resultType="Student"> * 增加了useCache="false" 相当于 局部关闭 2级缓存 useCache默认值为true===》把查询放入2级缓存 * 02.全局关闭 * 在mybatis.xml文件中增加 * <settings> * <!--全局关闭2级缓存 --> * <setting name="cacheEnabled" value="false"/> * </settings> */ @Test public void test3() { Student student = dao.selectStudentById(1); System.out.println(student); session.close(); //关闭了session 一级缓存中的数据肯定清空了 session = SessionUtil.getSession(); //再次获取session 查询数据 dao = session.getMapper(StudentDao.class); //这时候不会再有sql语句了 因为2级缓存中存在相同的查询(mapper文件中sql的id)和相同的sql语句 Student student2 = dao.selectStudentById(1); System.out.println(student2); } /** * 2级缓存的使用原则: * 01. 很少被修改的数据 * 02. 不是很重要的数据,允许出现偶尔并发的数据 * 03. 不会被并发访问的数据 * 04.多个namespace不能操作同一张表 * 05.不能在关联关系表上执行增删改操作 */