日日操夜夜添-日日操影院-日日草夜夜操-日日干干-精品一区二区三区波多野结衣-精品一区二区三区高清免费不卡

公告:魔扣目錄網(wǎng)為廣大站長(zhǎng)提供免費(fèi)收錄網(wǎng)站服務(wù),提交前請(qǐng)做好本站友鏈:【 網(wǎng)站目錄:http://www.ylptlb.cn 】, 免友鏈快審服務(wù)(50元/站),

點(diǎn)擊這里在線(xiàn)咨詢(xún)客服
新站提交
  • 網(wǎng)站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會(huì)員:747

作者最近在開(kāi)發(fā)公司項(xiàng)目時(shí)使用到 redis 緩存,并在翻看前人代碼時(shí),看到了一種關(guān)于 @Cacheable 注解的自定義緩存有效期的解決方案,感覺(jué)比較實(shí)用,因此作者自己拓展完善了一番后分享給各位。

Spring 緩存常規(guī)配置

Spring Cache 框架給我們提供了 @Cacheable 注解用于緩存方法返回內(nèi)容。但是 @Cacheable 注解不能定義緩存有效期。這樣的話(huà)在一些需要自定義緩存有效期的場(chǎng)景就不太實(shí)用。

按照 Spring Cache 框架給我們提供的 RedisCacheManager 實(shí)現(xiàn),只能在全局設(shè)置緩存有效期。這里給大家看一個(gè)常規(guī)的 CacheConfig 緩存配置類(lèi),代碼如下,

@EnableCaching
@Configuration
public class CacheConfig extends CachingConfigurerSupport {
    ...

    private RedisSerializer<String> keySerializer() {
        return new StringRedisSerializer();
    }

    private RedisSerializer<Object> valueSerializer() {
        return new GenericFastJsonRedisSerializer();
    }

    public static final String CACHE_PREFIX = "crowd:";

    @Bean
    public CacheManager cacheManager(RedisConnectionFactory redisConnectionFactory) {
        // 配置序列化(解決亂碼的問(wèn)題)
        RedisCacheConfiguration config = RedisCacheConfiguration.defaultCacheConfig()
                //設(shè)置key為String
                .serializeKeysWith(RedisSerializationContext.SerializationPAIr.fromSerializer(keySerializer()))
                //設(shè)置value為自動(dòng)轉(zhuǎn)Json的Object
                .serializeValuesWith(RedisSerializationContext.SerializationPair.fromSerializer(valueSerializer()))
                .computePrefixWith(name -> CACHE_PREFIX + name  + ":")
                .entryTtl(Duration.ofSeconds(600));
        RedisCacheWriter redisCacheWriter = RedisCacheWriter.nonLockingRedisCacheWriter(Objects.requireNonNull(redisConnectionFactory));
        return new RedisCacheManager(redisCacheWriter, config);
    }
}

這里面簡(jiǎn)單對(duì) RedisCacheConfiguration 緩存配置做一下說(shuō)明:

  1. serializeKeysWith():設(shè)置 Redis 的 key 的序列化規(guī)則。
  2. erializeValuesWith():設(shè)置 Redis 的 value 的序列化規(guī)則。
  3. computePrefixWith():計(jì)算 Redis 的 key 前綴。
  4. entryTtl():全局設(shè)置 @Cacheable 注解緩存的有效期。

那么使用如上配置生成的 Redis 緩存 key 名稱(chēng)是什么樣得嘞?這里用開(kāi)源項(xiàng)目 crowd-admin 的 ConfigServiceImpl 類(lèi)下 getValueByKey(String key) 方法舉例,

@Cacheable(value = "configCache", key = "#root.methodName + '_' + #root.args[0]")
@Override
public String getValueByKey(String key) {
    QueryWrApper<Config> wrapper = new QueryWrapper<>();
    wrapper.eq("configKey", key);
    Config config = getOne(wrapper);
    if (config == null) {
        return null;
    }
    return config.getConfigValue();
}

執(zhí)行此方法后,Redis 中緩存 key 名稱(chēng)如下,

crowd:configCache:getValueByKey_sys.name

Spring Cache 緩存注解這樣用,實(shí)在是太香了!圖片

TTL 過(guò)期時(shí)間是 287,跟我們?nèi)衷O(shè)置的 300 秒基本是一致的。此時(shí)假如我們想把 getValueByKey 方法的緩存有效期單獨(dú)設(shè)置為 600 秒,那我們?cè)撊绾尾僮鬣希?/p>

@Cacheable 注解默認(rèn)是沒(méi)有提供有關(guān)緩存有效期設(shè)置的。想要單獨(dú)修改 getValueByKey 方法的緩存有效期只能修改全局的緩存有效期。那么有沒(méi)有別的方法能夠?yàn)?nbsp;getValueByKey 方法單獨(dú)設(shè)置緩存有效期嘞?當(dāng)然是有的,大家請(qǐng)往下看。

自定義 MyRedisCacheManager 緩存

其實(shí)我們可以通過(guò)自定義 MyRedisCacheManager 類(lèi)繼承 Spring Cache 提供的 RedisCacheManager 類(lèi)后,重寫(xiě) createRedisCache(String name, RedisCacheConfiguration cacheConfig) 方法,代碼如下,

public class MyRedisCacheManager extends RedisCacheManager {
    public MyRedisCacheManager(RedisCacheWriter cacheWriter, RedisCacheConfiguration defaultCacheConfiguration) {
        super(cacheWriter, defaultCacheConfiguration);
    }

    @Override
    protected RedisCache createRedisCache(String name, RedisCacheConfiguration cacheConfig) {
        String[] array = StringUtils.split(name, "#");
        name = array[0];
         // 解析 @Cacheable 注解的 value 屬性用以單獨(dú)設(shè)置有效期
        if (array.length > 1) {
            long ttl = Long.parseLong(array[1]);
            cacheConfig = cacheConfig.entryTtl(Duration.ofSeconds(ttl));
        }
        return super.createRedisCache(name, cacheConfig);
    }
}

MyRedisCacheManager 類(lèi)邏輯如下,

  1. 繼承 Spring Cache 提供的 RedisCacheManager 類(lèi)。
  2. 重寫(xiě) createRedisCache(String name, RedisCacheConfiguration cacheConfig) 方法。
  3. 解析 name 參數(shù),根據(jù) # 字符串進(jìn)行分割,獲取緩存 key 名稱(chēng)以及緩存有效期。

接著我們修改下 CacheConfig 類(lèi)的 cacheManager 方法用以使用 MyRedisCacheManager 類(lèi)。代碼如下,

@Bean
public CacheManager cacheManager(RedisConnectionFactory redisConnectionFactory) {
    return new MyRedisCacheManager(RedisCacheWriter.nonLockingRedisCacheWriter(redisConnectionFactory), defaultCacheConfig());
}

private RedisCacheConfiguration defaultCacheConfig() {
    return RedisCacheConfiguration.defaultCacheConfig()
            .serializeKeysWith(RedisSerializationContext.SerializationPair.fromSerializer(keySerializer()))
            .serializeValuesWith(RedisSerializationContext.SerializationPair.fromSerializer(valueSerializer()))
            .computePrefixWith(name -> CACHE_PREFIX + name  + ":")
            .entryTtl(Duration.ofSeconds(600));
}

最后我們修改下 @Cacheable 注解使用方式,在原有 value 屬性的 configCache 值后添加 #600,單獨(dú)標(biāo)識(shí)緩存有效期。代碼如下,

@Cacheable(value = "configCache#600", key = "#root.methodName + '_' + #root.args[0]")
@Override
public String getValueByKey(String key) {
   ...
}

看下 getValueByKey 方法生成的 Redis 緩存 key 有效期是多久。如下,

Spring Cache 緩存注解這樣用,實(shí)在是太香了!圖片

OK,看到是 590 秒有效期后,我們就大功告成了,希望本文能對(duì)大家有所幫助

分享到:
標(biāo)簽:Spring
用戶(hù)無(wú)頭像

網(wǎng)友整理

注冊(cè)時(shí)間:

網(wǎng)站:5 個(gè)   小程序:0 個(gè)  文章:12 篇

  • 51998

    網(wǎng)站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會(huì)員

趕快注冊(cè)賬號(hào),推廣您的網(wǎng)站吧!
最新入駐小程序

數(shù)獨(dú)大挑戰(zhàn)2018-06-03

數(shù)獨(dú)一種數(shù)學(xué)游戲,玩家需要根據(jù)9

答題星2018-06-03

您可以通過(guò)答題星輕松地創(chuàng)建試卷

全階人生考試2018-06-03

各種考試題,題庫(kù),初中,高中,大學(xué)四六

運(yùn)動(dòng)步數(shù)有氧達(dá)人2018-06-03

記錄運(yùn)動(dòng)步數(shù),積累氧氣值。還可偷

每日養(yǎng)生app2018-06-03

每日養(yǎng)生,天天健康

體育訓(xùn)練成績(jī)?cè)u(píng)定2018-06-03

通用課目體育訓(xùn)練成績(jī)?cè)u(píng)定