RedisCacheManager无法更新keyspace_misses计数器

16
我正在使用spring-boot spring-data-redis 1.8.9.RELEASE的RedisCacheManager实现缓存,我想要知道一个指标:缓存命中/未命中比率。为了得到它,我提取了通过redis服务器暴露的keyspace_hits和keyspace_misses,也可以通过redis_cli使用INFO STATS查看。问题在于RedisCacheManager从不注册缓存未命中,即使有缓存“未命中”,keyspace_misses也不会增加。
调试代码后,我发现spring-data-redis在检索数据之前实际上会检查redis中是否存在该键EXISTS。我理解这种方法的意义,但是当执行EXISTS时,它并不会记录缓存未命中。
是否有任何方法可以使用RedisCacheManager并注册缓存未命中?我知道可以使用其他redis对象来完成此操作,但我想知道是否可以使用标准的CacheManager实现来完成。 编辑 理想的解决方案不会增加很大的开销,而且我无法编辑redis服务器的配置。
RedisCacheManager从缓存中检索元素时使用的代码。请注意Boolean exists
public RedisCacheElement get(final RedisCacheKey cacheKey) {
    Assert.notNull(cacheKey, "CacheKey must not be null!");
    Boolean exists = (Boolean)this.redisOperations.execute(new RedisCallback<Boolean>() {
        public Boolean doInRedis(RedisConnection connection) throws DataAccessException {
            return connection.exists(cacheKey.getKeyBytes());
        }
    });
    return !exists ? null : new RedisCacheElement(cacheKey, this.fromStoreValue(this.lookup(cacheKey)));
}

上述代码将在redis上执行这些命令,可以通过MONITOR在缓存未命中时查看。请注意,EXISTS将按照代码执行:

Redis commands executed for a cache miss

执行以上命令后,即使缓存未命中也不会增加{{keyspace_misses}}计数:

enter image description here


1
任何在空键上调用的阻塞操作(BLPOP、BRPOP 和 BRPOPLPUSH)都会导致 keyspace_misses 增加。 - mrdoubtful
你准备走多远?你可以从源代码构建Redis,并添加一行代码将EXISTS注册为缓存未命中。 - Imaskar
@Imaskar 感谢您的评论,但我无法对 Redis 服务器进行任何更改。 - Always Learning
@AlwaysLearning,你解决了你的问题吗?我们也遇到了同样的问题。你的意见会对我们有所帮助。我们正在使用以下版本的Redis:Redis服务器v=3.2.12。 - Prakash
@Prakash,很遗憾我没有找到可行的解决方案。 - Always Learning
1个回答

1

问题中提到的代码是Spring提供的RedisCache的一部分。

  1. 扩展并创建RedisCache类的自定义实现,以覆盖“get”方法的行为以满足您的需求。
  2. 扩展RedisCacheManager以覆盖“createRedisCache”方法,使用您在第一步中创建的自定义RedisCache而不是默认缓存。

感谢您的回复。您能提供可行的代码来证明您的答案吗?我已经看过了,但我没有看到实现上述目标的可行机制。 - Always Learning
1
我知道这个方法有点老,但我可以确认它是可行的。虽然不是所有的类和构造函数都是公共的,但是可以创建一个缓存装饰器,并创建一个缓存管理器来使用你的实现来装饰缓存。 - frisco

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接