SpringBoot2.x整合Redis Sentinel

redis sentinel搭建之后,在spring-boot项目中集成。

配置

在pom.xml文件中添加如下依赖配置(这里spring-boot版本2.2.5),这个版本中,默认使用lettuce作为redis连接池。

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>

<dependency>
    <groupId>org.apache.commons</groupId>
    <artifactId>commons-pool2</artifactId>
</dependency>

在application.yml添加如下redis sentinel、lettuce配置,对应的配置类是RedisProperties

spring:
  redis:
#    host: 127.0.0.1
#    port: 6380
    # 连接redis节点和sentinel的密码,
    password: passwd@190
    lettuce:
      pool:
        max-active: 20
        max-wait: -1
        max-idle: 10
        min-idle: 2
    sentinel:
      # redis主库别名配置,需要与哨兵配置中的主库别名一致
      master: master_node
      # 哨兵集群
      nodes:
        - 127.0.0.1:6390
        - 127.0.0.1:6391
        - 127.0.0.1:6393

集成

自动装配

在进行RedisProperties配置后,Spring Boot有一个自动装配的机制,步骤如下

  1. 配置Redis Connection Factory,用于管理Redis连接池。详见LettuceConnectionConfiguration
  2. 通过Redis Connection配置RedisTemplate,用于访问Redis。详见RedisAutoConfiguration

自动装配的方式适合在Redis单实例时使用,切换为sentinel架构后,在配置Redis Connection Factory中没有配置sentinel的访问密码,如果sentinel开启密码访问,会无法连接到sentinel集群。

在sentinel没有进行密码验证时,也只会对主库进行读写操作,无法做到主从库多节点访问。源码可见LettuceConnectionConfiguration.createLettuceConnectionFactory。

Redis Connection Factory

@Bean
@ConditionalOnMissingBean(RedisConnectionFactory.class)
LettuceConnectionFactory redisConnectionFactory(
      ObjectProvider<LettuceClientConfigurationBuilderCustomizer> builderCustomizers,
      ClientResources clientResources) throws UnknownHostException {
   LettuceClientConfiguration clientConfig = getLettuceClientConfiguration(builderCustomizers, clientResources,
         getProperties().getLettuce().getPool());
   return createLettuceConnectionFactory(clientConfig);
}

Redis Template

@Configuration(proxyBeanMethods = false)
@ConditionalOnClass(RedisOperations.class)
@EnableConfigurationProperties(RedisProperties.class)
@Import({ LettuceConnectionConfiguration.class, JedisConnectionConfiguration.class })
public class RedisAutoConfiguration {

   @Bean
   @ConditionalOnMissingBean(name = "redisTemplate")
   public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory)
         throws UnknownHostException {
      RedisTemplate<Object, Object> template = new RedisTemplate<>();
      template.setConnectionFactory(redisConnectionFactory);
      return template;
   }
}

手动装配

自动装配模式下创建的RedisConnectionFactory无法满足我们的需求,那么只能由我们自己自定义配置了。

创建一个RedisConnectionFactory Bean,并重写sentinel配置和lettuce client配置。

@Bean
public RedisConnectionFactory lettuceConnectionFactory(RedisProperties redisProperties) {

    // 读取sentinel配置
    String masterName = redisProperties.getSentinel().getMaster();
    List<String> sentinelNodeList = redisProperties.getSentinel().getNodes();
    RedisSentinelConfiguration sentinelConfiguration = new RedisSentinelConfiguration(masterName, new HashSet<>(sentinelNodeList));
    
    // 设置节点和哨兵访问密码 
    sentinelConfiguration.setPassword(redisProperties.getPassword());
    sentinelConfiguration.setSentinelPassword(redisProperties.getPassword());
    
    // lettuce client配置,在进行读取时,访问任意一个节点,默认读写都只从主节点进行
    LettucePoolingClientConfiguration clientConfig = LettucePoolingClientConfiguration
            .builder().readFrom(ReadFrom.ANY).build();
    
    LettuceConnectionFactory factory = new LettuceConnectionFactory(sentinelConfiguration, clientConfig);
    // 在获取连接时,先验证连接是否已经中断,如果已经中断则创建一个新的连接
    factory.setValidateConnection(true);
    return factory;
}

验证

启动spring-boot项目后,Lettuce Connection通过Sentinel获取到主从库节点信息,并与之进行连接。在创建连接时,根据lettuce pool配置,会对主从节点做负载均衡,让连接均衡分配到各个节点。我们主要测试的项目是

  • 写操作是否走的主库,读操作是否为任意主从库
  • 主库宕机后,是否可以正常工作,能不能从Sentinel获取主从切换信息,进行主库的重新设定

而要知道这些信息,就得查看lettuce的日志,而日志级别为logging.level.root=info时,是看不到这些信息的。

在application.yml中添加如下配置,将lettuce包的日志级别设置为debug。

logging:
  level:
    io.lettuce.core: debug

在配置好后重启项目,通过RedisTemplate做两个类型的操作,一个是Set、一个是Get。

验证写操作

连续执行多个Set操作,查看Lettuce日志,发现请求始终是发给主库的,符合预期。

验证读操作

连续执行多个Get操作,查看Lettuce日志,发现请求是发给任一主从库的,符合预期。

验证主从切换

将主库宕机后,哨兵检测到主库下线,然后重新选主后进行主从切换,这个过程正常的话几秒内完成。客户端从哨兵获取新的主从库信息,重新配置主从库节点。

  • 立即进行写操作,报无法连接redis的异常,符合预期
  • 立即进行读操作,可以正常响应,符合预期
  • 等待几秒后,进行读写操作,均可正常响应,符合预期。
posted @   cd_along  阅读(1139)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· DeepSeek “源神”启动!「GitHub 热点速览」
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· 我与微信审核的“相爱相杀”看个人小程序副业
· C# 集成 DeepSeek 模型实现 AI 私有化(本地部署与 API 调用教程)
· spring官宣接入deepseek,真的太香了~
点击右上角即可分享
微信分享提示