1. 程式人生 > >SpringBoot之快取

SpringBoot之快取

Spring從3.1開始定義了org.springframework.cache.Cacheorg.springframework.cache.CacheManager介面來統一不同的快取技術,並支援使用JCache(JSR-107)註解簡化我們開發;

Cache介面為快取的元件規範定義,包含快取的各種操作集合;
Cache介面下Spring提供了各種xxxCache的實現;如RedisCache,EhCacheCache , ConcurrentMapCache等;

每次呼叫需要快取功能的方法時,Spring會檢查指定引數的指定的目標方法是否已經被呼叫過;如果有就直接從快取中獲取方法呼叫後的結果,如果沒有就呼叫方法並快取結果後返回給使用者。下次呼叫直接從快取中獲取。

使用Spring快取抽象時我們需要關注以下兩點;

  1. 確定方法需要被快取以及他們的快取策略
  2. 從快取中讀取之前快取儲存的資料

這裡寫圖片描述

 * 將方法的執行結果進行快取,以後再要相同的資料,直接從快取中獲取,不用呼叫方法;
 * CacheManager管理多個Cache元件,對快取的真正CRUD操作是在Cache元件中進行的,每一個快取元件有自己唯一的名字
 *
 *
 * 原理:
 *   1、自動配置類;CacheAutoConfiguration
 *   2、快取的配置類
 *   org.springframework.boot.autoconfigure.cache.GenericCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.JCacheCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.EhCacheCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.HazelcastCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.InfinispanCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.CouchbaseCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.RedisCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.CaffeineCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.GuavaCacheConfiguration
 *   org.springframework.boot.autoconfigure.cache.SimpleCacheConfiguration【預設】
 *   org.springframework.boot.autoconfigure.cache.NoOpCacheConfiguration
 * 
 *   3、預設生效的配置類:SimpleCacheConfiguration;
 *
 *   4、給容器中註冊了一個CacheManager:ConcurrentMapCacheManager
 *   5、可以獲取和建立ConcurrentMapCache型別的快取元件;它的作用將資料儲存在ConcurrentMap中
 *
 *   執行流程:
 *   @Cacheable:
 *   1、方法執行之前,先去查詢Cache(快取元件),按照cacheNames指定的名字獲取;
 *      (CacheManager先獲取相應的快取),第一次獲取快取,如果沒有Cache元件會自動建立。
 *   2、去Cache中查詢快取的內容,使用一個key,預設就是方法的引數;
 *      key是按照某種策略生成的;預設是使用keyGenerator生成的,預設使用SimpleKeyGenerator生成key;
 *          SimpleKeyGenerator生成key的預設策略;
 *                  如果沒有引數;key=new SimpleKey();
 *                  如果有一個引數:key=引數的值
 *                  如果有多個引數:key=new SimpleKey(params);
 *   3、沒有查到快取,就呼叫目標方法;
 *   4、將目標方法返回的結果,放進快取中
 *
 *   @Cacheable標註的方法執行之前先來檢查快取中有沒有這個資料,預設按照引數的值作為key去查詢快取,
 *   如果沒有,就執行方法並將結果放入快取;以後再來呼叫,就可以直接使用快取中的資料

幾個重要概念&快取註解

Tables Are
CacheManager 快取管理器,管理各種快取(Cache)元件
Cache 快取介面,定義快取操作。實現有:RedisCache、EhCacheCache、ConcurrentMapCache等
@EnableCaching 開啟基於註解的快取
@Cacheable 主要針對方法配置,能夠根據方法的請求引數對其結果進行快取
@CacheEvict 清空快取
@CachePut 保證方法被呼叫,又希望結果被快取
keyGenerator 快取資料時key生成策略
serialize 快取資料時value序列化策略

重要註解

@EnableCaching

標註在啟動類上,開啟快取註解

@Cacheable

 *   @Cacheable標註的方法執行之前先來檢查快取中有沒有這個資料,預設按照引數的值作為key去查詢快取,
 *   如果沒有就執行方法並將結果放入快取;以後再來呼叫就可以直接使用快取中的資料;
 *
 *   核心:
 *      1)、使用CacheManager【ConcurrentMapCacheManager】按照名字得到Cache【ConcurrentMapCache】元件
 *      2)、key使用keyGenerator生成的,預設是SimpleKeyGenerator
 *
 *   幾個屬性:
 *      cacheNames/value:指定快取元件的名字,將方法的返回結果放在哪個快取中,是陣列的方式,可以指定多個快取;
 *
 *      key:快取資料使用的key,可以用它來指定。預設是使用方法引數的值  1-方法的返回值
 *              編寫SpEL :  #id :引數id的值  ===》 #a0  #p0  #root.args[0]
 *              getEmp[2] == #root.methodName+'['+#id+']'
 *
 *      keyGenerator:key的生成器;可以自己指定key的生成器的元件id,比如keyGenerator="myKeyGenerator"
 *              key/keyGenerator:二選一使用;
 *
 *      cacheManager:指定快取管理器;或者cacheResolver指定獲取解析器
 *
 *      condition:指定符合條件的情況下才快取;
 *              condition = "#id>0"
 *              condition = "#a0>1":第一個引數的值>1的時候才進行快取
 *
 *      unless:否定快取;當unless指定的條件為true,方法的返回值就不會被快取;可以獲取到結果進行判斷
 *              unless = "#result == null",當查詢結果為空時,不進行快取
 *              unless = "#a0==2",如果第一個引數的值是2,結果不快取
 * 
 *      sync:是否使用非同步模式

@CachePut

 * @CachePut:既呼叫方法,又更新快取資料,即同步更新快取
 * 修改了資料庫的某個資料,同時更新快取;
 * 
 * 執行時機:
 *  1、先呼叫目標方法
 *  2、將目標方法的結果快取起來
 *
 * 測試步驟:
 *  1、查詢1號員工,查到的結果會放在快取中;
 *          key:1  value:lastName:張三
 *  2、以後查詢還是之前的結果
 *  3、更新1號員工;【lastName:zhangsan,gender:0】
 *          將方法的返回值也放進快取了;
 *          key:傳入的employee物件  值:返回的employee物件;
 *  4、查詢1號員工?
 *      應該是更新後的員工;
 *          key = "#employee.id":使用傳入的引數的員工id;
 *          key = "#result.id":使用返回後的id
 *          注意:@Cacheable的key是不能用#result,因為其key在呼叫方法之前就生成了
 * 
 *      為什麼是沒更新之前的快取?【1號員工沒有在快取中更新】
 *      需要注意:放入快取的key需要一致,才能更新

@CacheEvict

 * @CacheEvict:快取清除
 * 
 *  key:指定要清除的資料
 * 
 *  allEntries:指定是否清除這個快取中所有的資料,預設為false
 * 
 *  beforeInvocation:快取的清除是否在方法執行之前執行
 *      預設為false:代表快取清除操作是在方法執行之後執行;如果出現異常,快取就不會清除
 *
 *  beforeInvocation = true:
 *      代表清除快取操作是在方法執行之前執行,無論方法是否出現異常,快取都清除

@Caching

用於組合前面三個註解,實現複雜的快取機制。

原始碼:

@Target({ElementType.METHOD, ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
public @interface Caching {
    Cacheable[] cacheable() default {};

    CachePut[] put() default {};

    CacheEvict[] evict() default {};
}

用法:

@Caching(
         cacheable = {
             @Cacheable(...)
         },
         put = {
             @CachePut(...),
             @CachePut(...)
         },
         evict = {
             @CacheEvict(...)
         }
)

@CacheConfig

標註於類上,統一指定該類下所有方法的共同屬性

原始碼:

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface CacheConfig {
    String[] cacheNames() default {};

    String keyGenerator() default "";

    String cacheManager() default "";

    String cacheResolver() default "";
}

自定義主鍵生成策略

@Configuration
public class MyCacheConfig {

    @Bean("myKeyGenerator")
    public KeyGenerator keyGenerator(){
        return new KeyGenerator(){
            @Override
            public Object generate(Object target, Method method, Object... params) {
                return method.getName()+"["+ Arrays.asList(params).toString()+"]";
            }
        };
    }
}

相關推薦

SpringBoot快取

Spring從3.1開始定義了org.springframework.cache.Cache和org.springframework.cache.CacheManager介面來統一不同的快取技術,並支援使用JCache(JSR-107)註解簡化我們開發; Ca

springboot專案叢集生成hash的key導致快取不一致。

場景: 叢集專案使用訪問策略使用的隨機,快取使用的redis,自定義key當傳入兩個引數以上時候,使用Arrays.deepHashCode來計算快取的key。 問題: 然後出現在機器1剛訪問過這個介面,redis也有快取,訪問到機器2的時候仍然走service方法,也就是沒有從redi

19-SpringBootRedis(六)——Redis快取實現

SpringBoot之Redis(六)——Redis快取實現 1. 新增maven依賴 2. 引數配置 3. 實體類 4. Dao 5. Service 6. Controller 7. 原始碼下載 1. 新增m

Springboot使用Redis做快取資料

一、新增Redis依賴 <?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.o

SpringBoot資料快取Cache操作

一、前言 快取要解決的問題:一個程式的瓶頸在於資料庫,我們也知道記憶體的速度是大大快於硬碟的速度的。當我們需要重複地獲取相同的資料的時候,我們一次又一次的請求資料庫或者遠端服務,導致大量的時間耗費在資料庫查詢或者遠端方法呼叫上,導致程式效能的惡化,這便是資料快取要解決的問題。

SpringBoot整合redis實現快取

主要程式碼: String key = "teacher_"+id; boolean hasKey = redisTemplate.hasKey(key); ValueOperations<String,Teacher> o

Springboot應用快取實踐:Ehcache加持

本文共 851字,閱讀大約需要 3分鐘 ! 本文內容腦圖如下: 概述 在如今高併發的網際網路應用中,快取的地位舉足輕重,對提升程式效能幫助不小。而3.x開始的 Spring也引入了對 Cache的支援,那對於如今發展得如火如荼的 Spring Boo

SpringBoot實戰(十三)快取

快取就是資料交換的緩衝區(又稱作Cache),當某一硬體要讀取資料時,會首先從快取中查詢需要的資料,找到了則直接執行,找不到的話則從記憶體中查詢。由於快取的執行速度比記憶體快得多,故快取的作用就是幫助硬體更快地執行。 因為快取往往使用的是RAM(斷電即掉的非永久性儲存),所以在用完後還是會把檔案送到硬碟等儲

SpringBootMybatis操作中使用Redis做快取

上一部落格學習了SpringBoot整合Redis,今天這篇部落格學習下Mybatis操作中使用Redis做快取。這裡其實主要學習幾個註解:@CachePut、@Cacheable、@CacheEvict、@CacheConfig。 一、基礎知識 @Cacheable @Cacheable 的作用 主要針對方

springboot本地快取(guava與caffeine)

1. 場景描述 因專案要使用本地快取,具體為啥不用redis等,就不討論,記錄下過程,希望能幫到需要的朋友。 2.解決方案 2.1 使用google的guava作為本地快取 初步的想法是使用google的guava,因為本身專案中就有guava的denpency。 2.1.1 pom檔案 需要3個depend

小白的springboot路(八)、繼承Redis以及@Cacheable註解實現Redis快取

0、前言   在專案中,快取作為一種高效的提升效能的手段,幾乎必不可少,Redis作為其中的佼佼者被廣泛應用; 一、spring boot整合Redis 1、新增依賴 <dependency> <groupId>org.spring

SpringBoot系列快取使用教程

介紹SpringBoot專案中使用快取,之前先介紹一下Spring的快取抽象和JSR107,本部落格是我在學習尚矽谷視訊和參考其它部落格之後做的筆記,僅供學習參考 @[toc] ## 一、Spring的快取抽象 ### 1.1、快取抽象定義 Spring從3.1開始定義了org.springframewor

初學SpringBoot

containe web ram cli compress 刷新 app use ping 原文教程鏈接在此http://blog.csdn.net/lxhjh/article/details/51752419。 使用了org.slf4j.Logger和org.slf4j.

springboot HelloController

mapping () mave 文件 code app ring hello 添加jar包 1、搭建環境   1.1 新建一個maven項目,一路下一步   1.2 打開pom 文件,首先增加<parent></parent>標簽: <p

springboot Spring Web Mvc Framework

fig ftl pathvaria nts bean ddr got del view 1、SpringMvc自動配置 Spring Boot 為SpringMvc提供了自動配置。 自動配置包含Spring的以下特征: (1)視圖解析器ContentNegotiatingV

Springboot 自定義配置文件及讀取配置文件

ebo hello path host 目錄 tps pre 示例 control 本文章來自【知識林】 讀取核心配置文件 核心配置文件是指在resources根目錄下的application.properties或application.yml配置文件,讀取這兩個配置文件

Eclipse搭建SpringBootHelloWorld

nbsp xml文件 blank itl depend ips autoconf pack bin 你的eclipse需要先安裝 Spring Tool Suite? 首先新建Maven工程 勾選第一個按鈕,第三個是選擇working set ,你可以不選 下一步,配

SpringBoot旅 -- 定時任務兩種(Spring Schedule 與 Quartz 整合 )實現

目的 config object cnblogs java title cor 進行 eat 相關文章 Spring Boot 相關文章目錄 前言 最近在項目中使用到定時任務,之前一直都是使用Quartz 來實現,最近看Spring 基礎發現其實Spring 提供

springBoot配置文件的讀取以及過濾器和攔截器的使用

boolean nco 定義 www cheng handle mod HR out 前言 在之前的學習springBoot中,成功的實現了Restful風格的基本服務。但是想將之前的工程作為一個項目來說,那些是僅僅不夠的。可能還需要獲取自定義的配置以及添加過濾器和攔截器。

SpringBoot配置google kaptcha

back put 是否 [] produce 邊框 驗證 servlet ray 項目中引入POM: <dependency> <groupId>com.google.code.kaptcha</groupId> <