1. 程式人生 > >mybatis 整合ehcache實現快取

mybatis 整合ehcache實現快取

mybatis 整合ehcache實現快取
   mybatis 一級快取和二級快取的區別:
1、一級快取:基於PerpetualCache的HashMap本地快取,其儲存作用域為同一個SqlSession,當Session flush或close之後,該Session中的所有Cache就將清空。
2、二級快取:與一級快取其機制相同,預設也是採用PerpetualCache,HashMap儲存,不同在於其儲存作用域為Mapper(Namespace),並且可自定義儲存源,如Ehcache。
3、對於快取資料更新機制,當某一個作用域(一級快取Session/二級快取Namespaces)的進行了C/U/D操作後,預設該作用域下所有select中的快取將被clear。
如果要實現MyBatis的二級快取,一般來說有如下兩種方式:
1. 採用MyBatis內建的Cache機制。
2. 採用三方Cache框架, 比如EhCache, OSCache等等。

  

一、導包:基於ssm---》新增ehcache-core-2.4.4.jar  mybatis-ehcache-1.0.0.jar 這兩個jar包(當前這兩個版本一致時可以實現,我之前兩個版本用其他的報錯,反正就是要匹配得上) (slf4j-api-1.6.2.jar和
   slf4j-log4j12-1.6.2.jar也要

<!--ehcache依賴slf4j--> <!--slf4j需要log4j-->

  二、檔案目錄 --新建ehcache.xml (目錄如下)


     <?xml version="1.0" encoding="UTF-8"?>
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="http://ehcache.org/ehcache.xsd">
<!-- java.io.tmpdir:Java臨時目錄。指定一個檔案目錄,當EhCache把資料寫到硬碟上或者系統jvm記憶體時,將把資料寫到這個檔案目錄下 -->
<diskStore path="java.io.tmpdir"/>
<!-- maxElementsInMemory:設定基於記憶體的快取可存放物件的最大數目。  -->
<!-- eternal:如果為true,表示物件永遠不會過期,此時會忽略timeToIdleSeconds和timeToLiveSeconds屬性,預設為false; -->
<!-- timeToIdleSeconds: 設定允許物件處於空閒狀態的最長時間,以秒為單位。當物件自從最近一次被訪問後,如果處於空閒狀態的時間超過了 -->
<!-- timeToIdleSeconds屬性值,這個物件就會過期。當物件過期,EHCache將把它從快取中清空。只有當eternal屬性為false,該屬性才有效。 -->
<!-- 如果該屬性值為0,則表示物件可以無限期地處於空閒狀態。  -->
<!-- timeToLiveSeconds:設定物件允許存在於快取中的最長時間,以秒為單位。當物件自從被存放到快取中後,如果處於快取中的時間超過了 timeToLiveSeconds屬性值,這個物件就會過期。當物件過期,EHCache將把它從快取中清除。只有當eternal屬性為false,該屬性才有效。如果該屬性值為0,則表示物件可以無限期地存在於快取中。timeToLiveSeconds必須大於timeToIdleSeconds屬性,才有意義。  -->
<!-- overflowToDisk:如果為true,表示當基於記憶體的快取中的物件數目達到了maxElementsInMemory界限後,會把益出的物件寫到基於硬碟的快取中。 -->
<!-- 設定快取的預設資料過期策略 -->
<defaultCache
maxElementsInMemory="10000" 
eternal="false" 
overflowToDisk="true"
timeToIdleSeconds="10"
timeToLiveSeconds="20"
diskPersistent="false"  
diskExpiryThreadIntervalSeconds="120"/>
<!--  自定義快取策略-學生資訊快取容器對應策略-->
<cache name="userCache"          
maxElementsInMemory="1000"  
eternal="false"             
overflowToDisk="true"       
timeToIdleSeconds="10"      
timeToLiveSeconds="20"/> 
   <!--  自定義快取策略-教師資訊快取容器對應策略-->  
<!--      <cache name="techerCache"          -->
<!--         maxElementsInMemory="1000"  -->
<!--         eternal="false"                 -->
<!--         overflowToDisk="true"       -->
<!--         timeToIdleSeconds="10"      -->
<!--         timeToLiveSeconds="20"/>        -->
</ehcache>
   三、 IUserMapper.xml 中新增下面(*mapper.xml想要哪些sql進行快取就在相應的xml裡面加)
<?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="com.user.dao.IUserMapper">
<resultMap type="com.user.entity.User" id="userMap">
   <id  property="id" column="id"/>
   <result property="name" column="name"/>
   <result property="psd" column="psd"/>
</resultMap>   
   <!--在mapper檔案中的頭部引入快取策略-->
   <!-- 以下兩個<cache>標籤二選一,第一個可以輸出日誌,第二個不輸出日誌 -->
   <!--   <cache type="org.mybatis.caches.ehcache.EhcacheCache" /> -->
<cache type="org.mybatis.caches.ehcache.LoggingEhcache"/> 

四、測試類:
        @RequestMapping("findUserList")
public String findUserList(HttpServletRequest request, Model model) {
User user1 = (User) request.getSession().getAttribute("user");
List<User> user = userService.findUserList(user1.getName());//第一次執行正常查詢
System.out.println("----------------------------start");
List<User> user22 = userService.findUserList(user1.getName()); //第二次執行從快取中獲取資料(列印sql如下)
System.out.println("----------------------------end");
model.addAttribute("userList", user);
return "user/userInformation";
}
五、執行該方法之後:第一次正常查詢,第二次獲取快取內資料

    如上就成功。

六、有個問題,

用spring管理 ehcache 和 直接在 mapper.xml 檔案裡面使用ehcache有什麼區別麼

整合玩ssm框架以後 加上 必要的ehcaceh的jar包,然後直接在整個usermapper.xml 檔案中增加 一行

<cache type="org.mybatis.caches.ehcache.LoggingEhcache" />

 就可以直接使用ehcache了

可是   還可以在 applicationContext.xml檔案中 增加 ehcaceh 管理

然後 使用@cacheable,spring 的粒度更細     這 兩者  有那些不一樣的地方。 有沒有人能說一下。