1. 程式人生 > >mybatis+redis+mybatis-redis實現二級快取

mybatis+redis+mybatis-redis實現二級快取

mybatis-redis原始碼: https://github.com/mybatis/redis-cache

mybatis-redis官網說明: http://www.mybatis.org/redis-cache/index.html

說明:

1、MyBatis預設開啟二級快取

2、MyBatis預設實現了自己的二級快取(PerpetualCache),內部使用HashMap實現,無法實現分散式,並且伺服器重啟後就沒有快取了。

3、MyBatis二級快取只適用於不常進行增、刪、改的資料,比如國家行政區省市區街道資料。一但資料變更,MyBatis會清空快取。因此二級快取不適用於經常進行更新的資料。

4、MyBatis二級快取是按名稱空間(namespace)進行快取的,可以指定某個名稱空間下的sql進行快取

5、MyBatis二級快取的物件必須實現Serializable介面

 

步驟(以下配置已專案中快取國家行政區省市區街道資料為例)

1、配置maven

配置jedis和mybatis-redis(實現了mybatis的cache介面的實現類),其他請自行配置(如:mybatis或mybatis-spring-boot-starter)
 

<!-- https://mvnrepository.com/artifact/redis.clients/jedis -->
        <dependency>
            <groupId>redis.clients</groupId>
            <artifactId>jedis</artifactId>
            <version>2.8.0</version>
        </dependency>
<!-- https://mvnrepository.com/artifact/org.mybatis.caches/mybatis-redis -->
        <dependency>
            <groupId>org.mybatis.caches</groupId>
            <artifactId>mybatis-redis</artifactId>
            <version>1.0.0-beta2</version>
        </dependency>

2、配置redis.properties

#redis的伺服器地址
host=127.0.0.1
#redis的服務埠
port=6379
#連結資料庫
default.db=0
#客戶端超時時間單位是毫秒
timeout=60000
#最大連線數
maxActive=300
#最大空閒數
maxIdle=100
#最小空閒數
minIdle=1
#最大建立連線等待時間
maxWait=1000
#指明是否在從池中取出連線前進行檢驗,如果檢驗失敗,則從池中去除連線並嘗試取出另一個
testOnBorrow=true
#當呼叫return Object方法時,進行有效性檢查
testOnReturn=true

3、配置AreaDefaultMapperExt.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.tyb.saas.common.dal.dao.AreaDefaultMapper">
 
    <!--
    flushInterval(清空快取的時間間隔): 單位毫秒,可以被設定為任意的正整數。
        預設情況是不設定,也就是沒有重新整理間隔,快取僅僅呼叫語句時重新整理。
    size(引用數目): 可以被設定為任意正整數,要記住你快取的物件數目和你執行環境的可用記憶體資源數目。預設值是1024。
    readOnly(只讀):屬性可以被設定為true或false。只讀的快取會給所有呼叫者返回快取物件的相同例項。
        因此這些物件不能被修改。這提供了很重要的效能優勢。可讀寫的快取會返回快取物件的拷貝(通過序列化)。這會慢一些,但是安全,因此預設是false。
    eviction(回收策略): 預設的是 LRU:
        1.LRU – 最近最少使用的:移除最長時間不被使用的物件。
        2.FIFO – 先進先出:按物件進入快取的順序來移除它們。
        3.SOFT – 軟引用:移除基於垃圾回收器狀態和軟引用規則的物件。
        4.WEAK – 弱引用:更積極地移除基於垃圾收集器狀態和弱引用規則的物件。
    blocking(是否使用阻塞快取): 預設為false,當指定為true時將採用BlockingCache進行封裝,blocking,阻塞的意思,
        使用BlockingCache會在查詢快取時鎖住對應的Key,如果快取命中了則會釋放對應的鎖,否則會在查詢資料庫以後再釋放鎖,
        這樣可以阻止併發情況下多個執行緒同時查詢資料,詳情可參考BlockingCache的原始碼。
    type(快取類):可指定使用的快取類,mybatis預設使用HashMap進行快取
    -->
    <cache type="org.mybatis.caches.redis.RedisCache" blocking="false"
           flushInterval="0" readOnly="true" size="1024" eviction="FIFO"/>
 
    <!--
        useCache(是否使用快取):預設true使用快取
    -->
    <select id="find" parameterType="map" resultType="com.tyb.saas.common.api.model.dto.RspAreaInfo" useCache="true">
        SELECT area_id AS areaId, area_name AS areaName
        FROM t_area_default
        WHERE 1=1
        <choose>
            <when test="areaParentId == null">
                AND area_level = 1
            </when>
            <otherwise>
                AND area_parent_id = #{areaParentId,jdbcType=INTEGER}
            </otherwise>
        </choose>
    </select>
 
</mapper>

注:如果只配置<cache />則使用的是mybatis的預設二級快取

 

如果只配置<cache type="org.mybatis.caches.redis.RedisCache" blocking="false" /> 則使用redis快取,其他配置按預設

如果使用了mybatis generator生成了AreaDefaultMapper.xml,由於同一個名稱空間只能配置一次快取,無法在這個xml再配置一個快取(會拋異常),因此這個xml要配:
 

<cache-ref namespace="com.tyb.saas.common.dal.dao.AreaDefaultMapper"/>

去引用AreaDefaultMapperExt.xml的快取

 

 

以上即可

 

QA

Q1:能不能使用註解進行配置?A:能

在dao層的實現層使用@CacheNamespace註解

@CacheNamespace( implementation = org.mybatis.caches.redis.RedisCache.class)

(由於我自己的專案用mybatis代理實現類,沒有dao的實現層,所有這個我沒測,直接在dao層架註解是沒用的)

Q2:能不能自己實現快取?A:能

MyBatis有提供Cache介面,自己實現Cache介面就行