【Redis】@CacheEvict 部分源码解读

源码地址: 

org.springframework.cache.interceptor.CacheAspectSupport

image.png

org.springframework.cache.interceptor.AbstractCacheInvoker

immediate属性就是beforeInvocation, 即是否立即删除, cache.clear() 则是执行删除缓存, cache.invalidate()最后也会执行clear方法

image.png

beforeInvocation

默认在@CacheEvict 方法成功执行之后再清除,这时候就会存在一个问题,也许你的注解方法成功执行了删除操作,但是后续代码抛出异常导致未能清除缓存,下次查询时依旧从缓存中去读取,这时查询到的结果值是删除操作之前的值,而设置beforeInvocation=true之后当执行这个方法之前执行清除缓存的操作,这样不管这个方法执行成功与否,该缓存都将不存在 (aop成功的前提下,缓存才会删除,有可能执行缓存清除失败)

allEntries

慎用注解的allEntries属性, 因为allEntries会根据传入的value属性拼成"${value}*"模糊匹配的字符串进行模糊匹配删除

org.springframework.data.redis.cache.RedisCache

this.cacheWriter.clean 方法执行的是 DefaultRedisCacheWriter.class#clean 方法, 这是spring-data-redis提供的默认实现类, 可以通过重写这个类改变redis操作逻辑

image.png

org.springframework.data.redis.cache.DefaultRedisCacheWriter

redis会先通过keys命令获取所有键值,然后再删除

image.png

 

redis在使用keys时会扫描全表,这会导致短时间内Redis的cpu和内存飙高,且因为Redis是单线程执行操作,所以同时会导致Redis请求阻塞

PS: redis 6.0 的多线程只是前面的协议解读部分使用了多线程,底层增删改查还是用的单线程

所以生产环境要慎用甚至禁用掉@CacheEvict , 通过调整缓存结构来规避使用keys命令

 

如果帮到你,请点个赞吧 O(∩_∩)O~

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值