文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

springboot增加注解缓存@Cacheable的实现

2024-04-02 19:55

关注

springboot增加注解缓存@Cacheable

业务层使用


@Cacheable(value = "dictionary#1800", key = "#root.targetClass.simpleName +':'+ #root.methodName +':'+ #code")
    public Object findByCode(String code) {
        //业务
    }

配置


import org.springframework.cache.Cache;
import org.springframework.data.redis.cache.RedisCache;
import org.springframework.data.redis.cache.RedisCacheManager;
import org.springframework.data.redis.core.RedisOperations; 
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
 
public class MyRedisCacheManager extends RedisCacheManager {  
    
    private static final String TTLSEPARATOR = "#";
    private final ConcurrentMap<String, Cache> cacheMap = new ConcurrentHashMap(16);
    
    private long defaultExpiration = 0;  
    public MyRedisCacheManager(RedisOperations redisOperations) {
        super(redisOperations);
    } 
 
    @Override
    public Cache getCache(String name) { 
        long expiredTime = defaultExpiration;
        if (name.contains(TTLSEPARATOR)) {
            String[] split = name.split(TTLSEPARATOR);
            String cacheName = split[0];
            try {
                expiredTime = Double.valueOf(split[1]).longValue();
            } catch (Exception e) {
                e.printStackTrace();
            }
            Cache cache = this.cacheMap.get(name);
            if (cache != null) {
                return cache;
            } else {
                synchronized (this.cacheMap) {
                    cache = this.cacheMap.get(name);
                    if (cache == null) {
                        cache = new RedisCache(cacheName, null, super.getRedisOperations(), expiredTime);
                        if (cache != null) {
                            cache = this.decorateCache(cache);
                            this.cacheMap.put(name, cache);
                        }
                    }
 
                    return cache;
                }
            }
        } 
        return super.getCache(name);
    }  
}

import com.fasterxml.jackson.annotation.JsonTypeInfo;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.cache.CacheManager;
import org.springframework.cache.annotation.CacheConfig;
import org.springframework.cache.annotation.CachingConfigurerSupport;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
 
@CacheConfig
@Configuration
@EnableCaching
public class RedisConfig extends CachingConfigurerSupport {
 
    @Bean
    public CacheManager cacheManager(RedisTemplate redisTemplate) {
        //设置序列化Key的实例化对象
        redisTemplate.setKeySerializer(new StringRedisSerializer());
        //设置序列化Value的实例化对象 
        ObjectMapper mapper = new ObjectMapper();
        mapper.findAndRegisterModules();
        mapper.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL, JsonTypeInfo.As.PROPERTY);
        GenericJackson2JsonRedisSerializer serializer = new GenericJackson2JsonRedisSerializer(mapper);
        redisTemplate.setValueSerializer(serializer);
        MyRedisCacheManager mrc = new MyRedisCacheManager(redisTemplate);
        return mrc;
    } 
}

@Cacheable注解的属性使用

cacheNames和value

指定缓存组件的名字,通过下面代码可以看出可以将返回结果放在哪个缓存中,可以通过数组的方式指定多个缓存


 
 @AliasFor("cacheNames")
 String[] value() default {};
 
 @AliasFor("value")
 String[] cacheNames() default {};

key

缓存数据的时候使用的key,它是用来指定对应的缓存,模拟使用方法参数值作为key的值。也可以使用SpEL表达式的值来指定


 
 String key() default "";
名称 位置 描述 示例
methodName root object 被调用的方法名称 #root.methodName
Method root object 被调用的方法 #root.method.name
Target root object 当前被调用的目标对象 #root.target
targetClass root object 当前被调用的目标对象类 #root.targetClass
args root object 被调用方法的参数列表#root.args[0]
caches root object 调用的缓存列表 #root.caches[0].name
argument name evaluation context 方法的参数名称可以直接使用#参数名 #p0,#a0等等
result evaluation context 执行方法后的返回值 #result

可以通过这个参数提示列表看看到这个key所支持的root object对象有哪些,通过这样的方式可以指定对应的key值。

在这里插入图片描述

keyGenerator

这个是表示指定的key的生成器,当然在之前分享中我们说过一个简单的key的生成策略。这里我们还可以通过自定的方式来实现这个key的生成策略。

keyGenerator

这个是表示指定的key的生成器,当然在之前分享中我们说过一个简单的key的生成策略。这里我们还可以通过自定的方式来实现这个key的生成策略。


import org.springframework.cache.interceptor.KeyGenerator;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.lang.reflect.Method;
import java.util.Arrays;
@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()+"]";
            }
        };
    }
}

在使用的时候可以通过一下的方式进行配置


@Cacheable(cacheNames = {"emp"},keyGenerator = "myKeyGenerator")

cacheManager指定缓存管理器

 String cacheManager() default "";
 
 String cacheResolver() default "";

condition

指定复合条件的情况下才缓存。也可以通过SpEL表达式进行设置。这个配置规则和上面表格中的配置规则是相同的。


 
 String condition() default "";

unless(除非)

当这个条件为true的时候,方法的返回值就不会被缓存。



 String unless() default "";

sync

是否异步



 boolean sync() default false;

注意

在使用这个属性的时候,当这个属性为true的时候,unless属性是不能使用的。


{@link #unless()} is not supported

以上为个人经验,希望能给大家一个参考,也希望大家多多支持编程网。

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     807人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     351人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     314人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     433人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     221人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯