You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot+Hibernate集成Redisson时Redis请求量过高求助

问题:低请求量下Redis操作量异常飙升(250 RPS对应8万次/秒Redis操作)

技术栈与配置信息

应用基于Spring Boot开发,采用Hibernate作为持久层框架,Redis作为缓存,通过Redisson实现缓存集成。

Spring Redis缓存配置

@Bean
public CacheManager cacheManager(RedissonClient redissonClient) {
        return new RedissonSpringCacheManager(redissonClient) {
            @Override
            public Cache getCache(String cacheName) {
                Cache cache = super.getCache(cacheName);
                return new RedisCacheWrapper(cache);
            }

            @Override
            protected CacheConfig createDefaultConfig() {
                CacheConfig cacheConfig = new CacheConfig(ttl, maxIdleTime);
                cacheConfig.setMaxSize(maxSize);
                return cacheConfig;
            }
        };
}

Hibernate实体缓存配置

@Cache(region = HIBERNATE_MY_REGION, usage = CacheConcurrencyStrategy.READ_WRITE)
public class MyEntity{
...
} 

依赖配置

<dependency>
    <groupId>org.redisson</groupId>
    <artifactId>redisson-hibernate-53</artifactId>
</dependency>
<dependency>
    <groupId>org.redisson</groupId>
    <artifactId>redisson</artifactId>
</dependency>

本地测试Redis性能截图

9秒内Redis性能分析

目前已将Redis切换为集群模式并添加从节点缓解压力,需定位问题根源并给出优化方案。


可能的问题根源

  • Hibernate二级缓存细粒度操作:READ_WRITE并发策略下,Hibernate可能对实体的每个属性或关联对象执行单独缓存操作,而非整体缓存实体。若实体存在多关联关系,会触发大量Redis请求。
  • Redisson缓存配置不合理:maxSize设置过小导致频繁缓存淘汰,引发大量删除、写入操作;TTL/MaxIdleTime过短导致缓存命中率极低,每次请求都需查询DB后写入Redis。
  • 缓存穿透/批量查询无优化:大量请求数据不在缓存中,穿透到DB后写入Redis;批量查询场景未做批量缓存操作,单个请求触发多次Redis交互。
  • 自定义RedisCacheWrapper冗余操作:RedisCacheWrapper可能在get/put流程中新增了不必要的Redis交互(如额外exists检查、日志相关操作)。
  • Hibernate缓存区域配置失效:多实体共用同一缓存区域或配置未生效,导致缓存无法复用,重复写入相同数据。

优化方案

调整Hibernate缓存策略

  • 若业务允许最终一致性,改用CacheConcurrencyStrategy.NONSTRICT_READ_WRITE,减少锁相关的Redis操作;确认READ_WRITE锁机制是否必要,排查Redisson实现是否存在过度锁交互。
  • 对实体关联对象(@OneToMany/@ManyToOne等)显式配置缓存,避免加载实体时单独查询关联数据触发缓存操作;或在Service层使用@Cacheable做粗粒度缓存,替代部分Hibernate二级缓存的细粒度操作。

优化Redisson缓存配置

  • 增大maxSize避免频繁缓存淘汰,根据业务访问模式调整TTL和MaxIdleTime,提升缓存命中率。
  • 启用Redisson本地缓存,对热点数据在应用本地做一级缓存,减少远程Redis调用:
    @Override
    protected CacheConfig createDefaultConfig() {
        CacheConfig cacheConfig = new CacheConfig(ttl, maxIdleTime);
        cacheConfig.setMaxSize(maxSize);
        // 配置本地缓存
        LocalCacheConfig localCacheConfig = new LocalCacheConfig();
        localCacheConfig.setTTL(10000); // 本地缓存有效期(毫秒)
        localCacheConfig.setMaxSize(1000); // 本地缓存最大容量
        cacheConfig.setLocalCacheConfig(localCacheConfig);
        return cacheConfig;
    }
    

解决缓存穿透与批量查询问题

  • 对不存在的ID请求添加空值缓存(设置较短TTL),避免频繁穿透到DB后写入Redis。
  • 针对批量查询场景实现批量缓存操作,一次性查询多个ID并批量写入缓存,减少Redis交互次数。

排查自定义RedisCacheWrapper

  • 审计RedisCacheWrapper代码,移除不必要的Redis操作(如额外的exists、get请求),确保仅在必要时与Redis交互。

监控与调优

  • 通过RedisInsight分析高频Redis命令类型(如是否大量HSET/HGET、DEL),定位操作来源。
  • 开启Hibernate缓存统计(hibernate.generate_statistics=true),分析缓存命中率、操作次数,确认是否由Hibernate二级缓存引发高频Redis调用。

内容的提问来源于stack exchange,提问作者Dmitry Shabalin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.31 04:21:48