從零到實現Shiro中Authorization和Authentication的緩存

本文大綱 html

  • 1、簡介
  • 2、緩存的概念
  • 3、自定義實現緩存機制
  • 4、什麼是Ehcache
  • 5、Ehcache怎麼用
  • 6、Spring對緩存的支持
  • 7、Spring+Ehcache實現
  • 8、Spring+Shiro+Ehcache實現
  • 9、總結

   

1、簡介 算法

在項目中,用到Shiro來作驗證受權的控制。但在實際使用的時候,發現用戶每訪問一個功能,都會從新到UserRealm中獲取一次權限。這樣子會花費大量的系統系統。此時就想到了使用緩存,查了一下,Shiro也確實支持AuthorizationAuthentication作緩存,那就果斷使用。 spring

但說到緩存,到底是怎麼一回事呢?這裏我將從零開始向你們介紹一下緩存。因爲網上已經有不少具體實現的文章了,本文內容是對緩存知識的逐步進階整理,目的是讓你們能從零開始對緩存進行了解,直到懂得如何實現Spring+Shiro+Ehcache的緩存配置。文章中不會重複網上能找到的一大堆內容,並會給出相關的參考文章給你們參考。 數據庫

   

2、緩存的概念 apache

一、緩存簡介 緩存

緩存,簡單來講,就是讓數據更接近於使用者。工做機制是:先從緩存中讀取數據,若是沒有再從慢速設備上(如數據庫)讀取實際數據(數據也會存入緩存)。 安全

2、緩存策略 服務器

緩存中數據都有必定的生命週期,何時移除、何時到期,都有必定的講究。主要分下面三點。 session

2.1 移除策略框架

移除策略,即若是緩存滿了,從緩存中移除數據的策略;常見的有LFU、LRU、FIFO:

FIFO(First In First Out):先進先出算法,即先放入緩存的先被移除;

LRU(Least Recently Used):最久未使用算法,使用時間距離如今最久的那個被移除;

LFU(Least Frequently Used):最近最少使用算法,必定時間段內使用次數(頻率)最少的那個被移除;

2.2 TTLTime To Live

存活期,即從緩存中建立時間點開始直到它到期的一個時間段(無論在這個時間段內有沒有訪問都將過時)

2.3 TTITime To Idle

空閒期,即一個數據多久沒被訪問將從緩存中移除的時間。

3、參考資料

可參看此文的緩存簡介:http://jinnianshilongnian.iteye.com/blog/2001040

   

3、自定義實現緩存機制

1 實現步驟

實現簡單的緩存機制,一般只需實現下面四點:

  1. 肯定用什麼來作cache,一般使用ConcurrentHashMap鍵值對來作cache。
  2. 建立緩存管理器CacheManager,緩存管理器主要實現如下內容:
    1. 建立一個cache並進行管理
    2. 經過key來獲取value的方法
    3. 根據key更新或新增緩存中的記錄的方法
    4. 根據key來刪除緩存中一條記錄的方法
    5. 清空緩存中的全部記錄的方法
  3. Service實現類中,當查詢內容的時候,先查詢緩存中的內容,如有,則返回;若無,則查詢數據庫中的內容,同時將查詢結果加到緩存中。
  4. 在數據庫數據有更新的時候,注意調用方法更新緩存中的數據。

只要選擇好cache,和建立好CacheManager,就能夠在Service中,經過建立CacheManager來管理緩存了。

2 存在問題

但咱們本身作出來的緩存因爲比較簡單考慮得沒那麼全面,因此問題也很多,如:

  1. 與業務邏輯代碼耦合度很高,須要在Service的方法中調用CacheManager的不少邏輯,不便於維護。
  2. 程序不夠靈活,沒法根據不一樣的條件進行緩存。
  3. 沒有完善的移除策略,須要開發人員在業務邏輯中進行控制,難以維護。
  4. 不通用,沒法使用第三方提供的緩存框架。

等等。

3 參考資料

因爲網上已有不少實現的文章,這裏不作重複。例如可參考:

http://blog.csdn.net/fanzhanwei/article/details/44958297

   

4、什麼是Ehcache

上一節是自定義緩存的實現,能夠看出,本身能夠作一個簡單的緩存,可是不夠完善。其實已經有不少第三方的緩存框架,有完善的機制,能夠給咱們使用,而ehcache就是這樣一種緩存框架。

1 Ehcache簡介

EhCache是一個純Java的進程內緩存框架,具備快速、精幹等特色,也是Hibernate中默認的CacheProvider。它會把查出來的數據存儲在內存或者磁盤中,以節省查詢數據庫的壓力。

2 Ehcache使用條件

  • 比較少更新的表數據

    由於若是更新很頻繁的數據,那就沒有緩存的必要了,可能還會增長開銷呢。

  • 對數據一致性要求不高的狀況

    據說Ehcache的同步不是很完善,會形成不一樣服務器上的Ehcache緩存同步未必及時,這樣可能會形成用戶在獲取數據的時候不一致。

3 Ehcache使用場景

  • 頁面緩存
  • 對象緩存
  • 數據庫數據緩存

   

5、Ehcache怎麼用

1 Ehcache使用步驟

使用Ehcache,基本步驟以下:

  1. 建立一個ehcache.xml的配置文件,裏面會有磁盤緩存位置、緩存配置等信息。
  2. 建立CacheManager,並讀取相應的xml配置
    1. 直接CacheManager cacheManage = new CacheManager(),讀取默認配置文件。
    2. 經過靜態方法create()建立,加載默認配置。
    3. 經過newInstance()工廠方法建立,newInstance()會有幾個重載,能夠傳入String、URL、InputStream等來加載配置文件。
  3. 建立Cache,能夠在ehcache.xml等配置文件中配置好,也能夠直接經過API建立cache,而後經過cacheManager.addCache()方法將cache加到緩存管理器中。
  4. 經過cacheManager.getCache()方法獲取Cache
  5. 建立Element對象,存放鍵值對。
  6. 將建立的Element對象存放到cache中。
  7. 經過以上步驟,就已經把緩存弄好並存了相關內容到緩存中了。要想得到緩存中的內容,就逆向操做,先使用cache.get()Element獲取出來,接着經過Element.getObjectValue()獲取到相應的值。

2 Ehcache配置文件

關於配置文件,默認狀況下會加載classpath下名爲ehcache.xml的配置文件。若是加載失敗,會加載Ehcache報中的ehcache-failsafe.xml文件,這個文件中含有簡單的默認配置。

ehcache.xml配置文件中,須要瞭解各參數的意思,如下是一個範例:

  • name:緩存名稱。
  • maxElementsInMemory:緩存最大個數。
  • eternal:緩存中對象是否爲永久的,若是是,超時設置將被忽略,對象從不過時。
  • timeToIdleSeconds:置對象在失效前的容許閒置時間(單位:秒)。僅當eternal=false對象不是永久有效時使用,可選屬性,默認值是0,也就是可閒置時間無窮大。
  • timeToLiveSeconds:緩存數據的生存時間(TTL),也就是一個元素從構建到消亡的最大時間間隔值,這隻能在元素不是永久駐留時有效,若是該值是0就意味着元素能夠停頓無窮長的時間。
  • maxEntriesLocalDisk:當內存中對象數量達到maxElementsInMemory時,Ehcache將會對象寫到磁盤中。
  • overflowToDisk:內存不足時,是否啓用磁盤緩存。
  • diskSpoolBufferSizeMB:這個參數設置DiskStore(磁盤緩存)的緩存區大小。默認是30MB。每一個Cache都應該有本身的一個緩衝區。
  • maxElementsOnDisk:硬盤最大緩存個數。
  • diskPersistent:是否在VM重啓時存儲硬盤的緩存數據。默認值是false
  • diskExpiryThreadIntervalSeconds:磁盤失效線程運行時間間隔,默認是120秒。
  • memoryStoreEvictionPolicy:當達到maxElementsInMemory限制時,Ehcache將會根據指定的策略去清理內存。默認策略是LRU(最近最少使用)。你能夠設置爲FIFO(先進先出)或是LFU(較少使用)。
  • clearOnFlush:內存數量最大時是否清除。

3 參考資料

具體例子可參考此網站:http://www.cnblogs.com/jingmoxukong/p/5975994.html

   

6、Spring對緩存的支持

1 Spring配置

Spring自己有對緩存方案的簡單實現,可經過註釋驅動來實現緩存機制。緩存中,最重要的兩個概念就是CacheManagerCacheSpring中的實現分別是:

  • CacheManagerorg.springframework.cache.support.SimpleCacheManager
  • Cacheorg.springframework.cache.concurrent.ConcurrentMapCacheFactoryBean

另外加上緩存的註解驅動配置:<cache:annotation-driven />

因此關鍵的spring xml配置文件以下:

2 重要註釋

Spring緩存中,關鍵是在方法中增長@Cacheable@CachePut@CacheEvict三個註釋,而後方法內注意實現業務邏輯就好,無需像《第二部分:自定義實現緩存機制》那樣子要參雜不少的緩存管理邏輯,這就是第三方緩存框架的一大好處。實際上Spring是經過Spring AOP,在方法的調用先後,分別攔截參數和返回值,來實現緩存的錄入的。關於上面上個註釋的做用以下:

  • @Cacheable:主要針對方法配置,可以根據方法的請求參數對其結果進行緩存。
  • @CachePut:主要針對方法配置,可以根據方法的請求參數對其結果進行緩存,和@Cacheable不一樣的是,它每次都會觸發真實方法的調用。
  • @CacheEvict,主要針對方法配置,可以根據必定的條件對緩存進行清空。

具體例子可參考此網站:https://www.ibm.com/developerworks/cn/opensource/os-cn-spring-cache/

   

7、Spring+Ehcache實現

Spring cache能知足一些基本的緩存需求,但若是需求複雜了,用戶量上去了,或者性能要求高了,Spring cache就估計難以支持了。由於它不支持高可用性,也不具有持久化數據的能力,這個時候就須要用到第三方的緩存方案,但仍是用Spring的API,代碼無需改動。這就是最理想的狀態了,而Spring也支持這一點。

要配置實用Ehcache,主要改動Springxml配置文件,將cacheManager這個bean的具體實現由org.springframework.cache.support.SimpleCacheManager改成org.springframework.cache.ehcache.EhCacheCacheManager,並引用org.springframework.cache.ehcache.EhCacheManagerFactoryBean這個bean。此兩個類的做用:

org.springframework.cache.ehcache.EhCacheManagerFactoryBean:加載Ehcache配置文件。

org.springframework.cache.ehcache.EhCacheCacheManager:支持net.sf.ehcache.CacheManager

配置文件以下:

具體例子可參考此網站:http://www.cnblogs.com/jingmoxukong/p/5975994.html

   

8、Spring+Shiro+Ehcache實現

1 配置cacheManager

若是要集成Shiro,這裏又得在Springxml配置文件中修改一下cacheManager的實現類,將其改成org.apache.shiro.cache.ehcache.EhCacheManager。以下:

 

<!-- 緩存管理器 使用Ehcache實現 -->
<bean id="cacheManager" class="org.apache.shiro.cache.ehcache.EhCacheManager">
  <property name="cacheManagerConfigFile" value="classpath:ehcache.xml"/>
</bean>

 

這樣就可使用適合shiroEhcacheCacheManager了。

2 配置Realm

修改Realmbean,指定其cache相關屬性的值,以下:

<!-- Realm實現 -->
<bean id="userRealm" class="com.huangzijian.realm.UserRealm">
  <property name="cachingEnabled" value="true"/>
  <property name="authenticationCachingEnabled" value="true"/>
  <property name="authenticationCacheName" value="authenticationCache"/>
  <property name="authorizationCachingEnabled" value="true"/>
  <property name="authorizationCacheName" value="authorizationCache"/>
</bean>

注意此處的cacheName,就是指在Ehcache中配置的cache,也就是一般在ehcache.xml中定義的cacahe

3 配置securityManager

須要在securityManager中配置cacheManager屬性,引用配好的cacheManager,以下:

<!-- 安全管理器 -->
<bean id="securityManager" class="org.apache.shiro.mgt.DefaultSecurityManager">
  <property name="realms">
    <list>
      <
ref bean="userRealm"/>
    </
list>   </property>   <property name="sessionManager" ref="sessionManager"/>   <property name="cacheManager" ref="cacheManager"/> </bean>

通過上面三步,便可激活ShiroAuthenticationAuthorization的緩存機制,從而沒必要要每次都讀取數據庫來肯定該人員的角色之類的,極大的節省了資源。

   

9、總結

經過上述一步一步的進階,相信你們均可以實現本身想要的緩存了。本文是經過要實現shiro中的AuthorizationAuthentication緩存,來逐步讓你們接觸起緩存的使用。對於緩存的使用,還有不少更深刻的內容,這裏只作了拋磚引玉,有待你們之後的使用瞭解了。

相關文章
相關標籤/搜索