springboot2.0重写RedisCacheMange自定义设置过期时间

@Override
@Cacheable(cacheNames = "cache#45", key = "#key")
public String test(String key) {
    System.out.println(key);
    return "12345";
}

通过cacheNames所传递的值进行处理来设置过期时间,如:cache#45  cache代表原来的前缀, #45 表示45秒的存活时间

实现:1.重新实现RedisCache

package com.sixi.ordercenter.business.config;

import com.google.common.base.Splitter;
import com.google.common.collect.Lists;
import org.springframework.data.redis.cache.RedisCache;
import org.springframework.data.redis.cache.RedisCacheConfiguration;
import org.springframework.data.redis.cache.RedisCacheWriter;

import java.time.Duration;
import java.util.List;
import java.util.regex.Pattern;

/**
 * @author : chenjie
 * @date : 2019-09-30 13:44
 */
public class CustomizeRedisCache extends RedisCache {
    private RedisCacheWriter cacheWriter;
    private RedisCacheConfiguration configuration;
    //校验规则:获取时间
    String REGEX_STR = ".*\\#\\d+$";


    /**
     * Create new {@link RedisCache}.
     *
     * @param name             must not be {@literal null}.
     * @param redisCacheWriter must not be {@literal null}.
     * @param cacheConfig      must not be {@literal null}.
     */
    protected CustomizeRedisCache(String name, RedisCacheWriter redisCacheWriter, RedisCacheConfiguration cacheConfig) {
        super(name, redisCacheWriter, cacheConfig);
        cacheWriter = redisCacheWriter;
        configuration = cacheConfig;
    }

    /** 主要实现逻辑 **/
    @Override
    public void put(Object key, Object value) {
        String name = super.getName();
        //是否按照指定的格式
        if (Pattern.matches(REGEX_STR, name)) {
            List<String> keyList = Lists.newArrayList(Splitter.on("#").split(name));
            String finalName = keyList.get(0);
            Long ttl = Long.valueOf(keyList.get(1));

            Object cacheValue = preProcessCacheValue(value);
            if (!isAllowNullValues() && cacheValue == null) {

                throw new IllegalArgumentException(String.format(
                        "Cache '%s' does not allow 'null' values. Avoid storing null via '@Cacheable(unless=\"#result == null\")' or configure RedisCache to allow 'null' via RedisCacheConfiguration.",
                        name));
            }
            //插入时添加时间
            cacheWriter.put(finalName, serializeCacheKey(createMyCacheKey(key)), serializeCacheValue(cacheValue), Duration.ofSeconds(ttl));
        } else {
            //原来逻辑处理
            super.put(key, value);
        }
    }
    /** 用户key的生成时不含有#45的前缀 **/
    protected String createMyCacheKey(Object key) {
        String convertedKey = convertKey(key);
        if (!configuration.usePrefix()) {
            return convertedKey;
        }
        return prefixCacheKey(convertedKey);
    }
    /** 去除下#45 的格式影响 **/
    private String prefixCacheKey(String key) {
        String name = super.getName();
        if (Pattern.matches(REGEX_STR, name)) {
            List<String> keyList = Lists.newArrayList(Splitter.on("#").split(name));
            String finalName = keyList.get(0);
            return configuration.getKeyPrefixFor(finalName) + key;
        }
        // allow contextual cache names by computing the key prefix on every call.
        return configuration.getKeyPrefixFor(name) + key;
    }
}

2.实现RedisCacheManager 

import org.springframework.data.redis.cache.RedisCache;
import org.springframework.data.redis.cache.RedisCacheConfiguration;
import org.springframework.data.redis.cache.RedisCacheManager;
import org.springframework.data.redis.cache.RedisCacheWriter;

import java.util.Map;

/**
 * @author : chenjie
 * @date : 2019-09-30 15:31
 */
public class MyRedisCacheManage extends RedisCacheManager {
    private final RedisCacheWriter cacheWriter;
    private final RedisCacheConfiguration defaultCacheConfig;
    
    /** 用于返回自定义的redisCache **/
    @Override
    protected RedisCache createRedisCache(String name, RedisCacheConfiguration cacheConfig) {
        return new CustomizeRedisCache(name, cacheWriter, cacheConfig != null ? cacheConfig : defaultCacheConfig);

    }

    public MyRedisCacheManage(RedisCacheWriter cacheWriter, RedisCacheConfiguration defaultCacheConfiguration) {
        super(cacheWriter, defaultCacheConfiguration);
        this.cacheWriter = cacheWriter;
        this.defaultCacheConfig = defaultCacheConfiguration;
    }

    public MyRedisCacheManage(RedisCacheWriter cacheWriter, RedisCacheConfiguration defaultCacheConfiguration, String... initialCacheNames) {
        super(cacheWriter, defaultCacheConfiguration, initialCacheNames);
        this.cacheWriter = cacheWriter;
        this.defaultCacheConfig = defaultCacheConfiguration;
    }

    public MyRedisCacheManage(RedisCacheWriter cacheWriter, RedisCacheConfiguration defaultCacheConfiguration, boolean allowInFlightCacheCreation, String... initialCacheNames) {
        super(cacheWriter, defaultCacheConfiguration, allowInFlightCacheCreation, initialCacheNames);
        this.cacheWriter = cacheWriter;
        this.defaultCacheConfig = defaultCacheConfiguration;
    }

    public MyRedisCacheManage(RedisCacheWriter cacheWriter, RedisCacheConfiguration defaultCacheConfiguration, Map<String, RedisCacheConfiguration> initialCacheConfigurations) {
        super(cacheWriter, defaultCacheConfiguration, initialCacheConfigurations);
        this.cacheWriter = cacheWriter;
        this.defaultCacheConfig = defaultCacheConfiguration;
    }

    public MyRedisCacheManage(RedisCacheWriter cacheWriter, RedisCacheConfiguration defaultCacheConfiguration, Map<String, RedisCacheConfiguration> initialCacheConfigurations, boolean allowInFlightCacheCreation) {
        super(cacheWriter, defaultCacheConfiguration, initialCacheConfigurations, allowInFlightCacheCreation);
        this.cacheWriter = cacheWriter;
        this.defaultCacheConfig = defaultCacheConfiguration;
    }

}

3.注入容器中

@Bean
public RedisCacheManager cacheManager(RedisConnectionFactory redisConnectionFactory) {
    //初始化一个RedisCacheWriter
    RedisCacheWriter redisCacheWriter = RedisCacheWriter.nonLockingRedisCacheWriter(redisConnectionFactory);
    //设置CacheManager的值序列化方式为json序列化
    RedisSerializer<Object> jsonSerializer = new GenericFastJsonRedisSerializer();
    RedisSerializationContext.SerializationPair<Object> pair = RedisSerializationContext.SerializationPair.fromSerializer(jsonSerializer);
    RedisCacheConfiguration defaultCacheConfig = RedisCacheConfiguration.defaultCacheConfig().serializeValuesWith(pair);
    //初始化RedisCacheManager
    return new MyRedisCacheManage(redisCacheWriter, defaultCacheConfig);
}

逻辑比较简单,只是在插入时把cacheNames中的值包含过期时间进行传递,然后获取设置就行

发布了85 篇原创文章 · 获赞 6 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/New_CJ/article/details/101779826