Redis 多数据源配置

在同一个应用中可能会同时用到多个redis数据源,并且这多个redis数据源可能模式还不一样,有单实例、集群、哨兵。

本文章就把这3种模式的redis数据源都集成到一个应用种。

那么就可以应付其他各种情况,例如,2个单实例3个集群4个哨兵等等。

pom

<dependency>
	<groupId>org.apache.commons</groupId>
    <artifactId>commons-pool2</artifactId>
</dependency>
<!-- redis-->
<dependency>
<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-data-redis</artifactId>
	</dependency>
<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-data-redis-reactive</artifactId>
</dependency>

yml

spring:  
  application: 
    name: two
  #默认用集群配置,3主3从共6节点的集群
  redis:
    timeout: 6000ms
    database: 10 
#    host: localhost #单实例redis用这个配置
#    password: #单实例redis用这个配置
    port: 6379 #单实例redis用这个配置
    password: Redis@123
    cluster: #集群用这个配置
      nodes:
        - 127.0.0.1:7011
        - 127.0.0.1:7012
        - 127.0.0.1:7013
        - 127.0.0.1:7014
        - 127.0.0.1:7015
        - 127.0.0.1:7016
      max-redirects: 2 #获取失败 最大重定向次数
    lettuce:
      pool: 
        max-active: 1000 #连接池最大连接数(使用负值表示没有限制)
        max-idle: 10 #连接池中的最大空闲连接
        min-idle: 3 #连接池中的最小空闲连接
        max-wait: -1 #连接池最大阻塞等待时间(使用负值表示没有限制)
  #redis单实例。单实例比较简单,ip,端口,密码,连接池就ok
  redis2:
    timeout: 6000ms
    database: 0 
    host: localhost #单实例redis用这个配置
    password: #单实例redis用这个配置
    port: 6379 #单实例redis用这个配置
    lettuce:
      pool: 
        max-active: 1000 #连接池最大连接数(使用负值表示没有限制)
        max-idle: 10 #连接池中的最大空闲连接
        min-idle: 3 #连接池中的最小空闲连接
        max-wait: -1 #连接池最大阻塞等待时间(使用负值表示没有限制)
  #redis哨兵.一主2从192.168.10.1:6379,192.168.10.2:6379,192.168.10.3:6379。三哨兵192.168.10.1:26379,192.168.10.2:26379,192.168.10.3:26379
  redis3:
    timeout: 6000ms
    database: 0 
    host: 192.168.10.1 #主节点的master
    password: ha@123 #redis密码
    port: 6379 #主节点的master端口
    lettuce:
      pool: 
        max-active: 1000 #连接池最大连接数(使用负值表示没有限制)
        max-idle: 10 #连接池中的最大空闲连接
        min-idle: 3 #连接池中的最小空闲连接
        max-wait: -1 #连接池最大阻塞等待时间(使用负值表示没有限制)
    sentinel: 
      master: mymaster 
      nodes: 
        - 192.168.10.1:26379
        - 192.168.10.2:26379
        - 192.168.10.3:26379

java配置:

需要3个读取yml的配置类,分别对应集群redis,单实例redis,哨兵redis。

package com.example.two.config.redis;
 
import java.util.List;
 
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
 
import lombok.Data;
 
/**
 * 映射redis的集群配置
 * yml:
  #默认用集群配置,3主3从共6节点的集群
spring: 
  redis:
    timeout: 6000ms
    database: 10 
    port: 6379 #单实例redis用这个配置
    password: Redis@123
    cluster: #集群用这个配置
      nodes:
        - 127.0.0.1:7011
        - 127.0.0.1:7012
        - 127.0.0.1:7013
        - 127.0.0.1:7014
        - 127.0.0.1:7015
        - 127.0.0.1:7016
      max-redirects: 2 #获取失败 最大重定向次数
    lettuce:
      pool: 
        max-active: 1000 #连接池最大连接数(使用负值表示没有限制)
        max-idle: 10 #连接池中的最大空闲连接
        min-idle: 3 #连接池中的最小空闲连接
        max-wait: -1 #连接池最大阻塞等待时间(使用负值表示没有限制) 
        
 * @author lsy
 *
 */
//@Data
@ConfigurationProperties(prefix="spring.redis.cluster")
public class RedisConfigOne {
 
    @Value("${spring.redis.host:127.0.0.1}")
    private String host;
    @Value("${spring.redis.port:6379}")
    private int port;
    @Value("${spring.redis.password:redis123}")
    private String password;
    @Value("${spring.redis.timeout:6000}")
    private int timeout;
    @Value("${spring.redis.database:0}")
    private int database;
    
    //pool映射
    @Value("${spring.redis.lettuce.pool.max-active}")
    private int maxActive;
    @Value("${spring.redis.lettuce.pool.max-idle}")
    private int maxIdle;
    @Value("${spring.redis.lettuce.pool.min-idle}")
    private int minIdle;
    @Value("${spring.redis.lettuce.pool.max-wait}")
    private int maxWait;
    
    //cluster映射
    List<String> nodes;//@ConfigurationProperties(prefix="spring.redis.cluster")映射
    
    @Value("${spring.redis.cluster.max-redirects:3}")
    private int maxRedirects;
 
    
    
    
    
	public String getHost() {
		return host;
	}
 
	public void setHost(String host) {
		this.host = host;
	}
 
	public int getPort() {
		return port;
	}
 
	public void setPort(int port) {
		this.port = port;
	}
 
	public String getPassword() {
		return password;
	}
 
	public void setPassword(String password) {
		this.password = password;
	}
 
	public int getTimeout() {
		return timeout;
	}
 
	public void setTimeout(int timeout) {
		this.timeout = timeout;
	}
 
	public int getDatabase() {
		return database;
	}
 
	public void setDatabase(int database) {
		this.database = database;
	}
 
	public int getMaxActive() {
		return maxActive;
	}
 
	public void setMaxActive(int maxActive) {
		this.maxActive = maxActive;
	}
 
	public int getMaxIdle() {
		return maxIdle;
	}
 
	public void setMaxIdle(int maxIdle) {
		this.maxIdle = maxIdle;
	}
 
	public int getMinIdle() {
		return minIdle;
	}
 
	public void setMinIdle(int minIdle) {
		this.minIdle = minIdle;
	}
 
	
 
	public List<String> getNodes() {
		return nodes;
	}
 
	public void setNodes(List<String> nodes) {
		this.nodes = nodes;
	}
 
	public int getMaxWait() {
		return maxWait;
	}
 
	public void setMaxWait(int maxWait) {
		this.maxWait = maxWait;
	}
 
	public int getMaxRedirects() {
		return maxRedirects;
	}
 
	public void setMaxRedirects(int maxRedirects) {
		this.maxRedirects = maxRedirects;
	}
 
    
    
}
package com.example.two.config.redis;
 
import java.util.List;
 
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
 
import lombok.Data;
 
/**
 * 映射redis的单实例配置配置
 * yml:
   #redis单实例。单实例比较简单,ip,端口,密码,连接池就ok
spring: 
  redis2:
    timeout: 6000ms
    database: 0 
    host: localhost #单实例redis用这个配置
    password: #单实例redis用这个配置
    port: 6379 #单实例redis用这个配置
    lettuce:
      pool: 
        max-active: 1000 #连接池最大连接数(使用负值表示没有限制)
        max-idle: 10 #连接池中的最大空闲连接
        min-idle: 3 #连接池中的最小空闲连接
        max-wait: -1 #连接池最大阻塞等待时间(使用负值表示没有限制)
 
 * @author lsy
 *
 */
//@Data
@ConfigurationProperties(prefix="spring.redis2.cluster")
public class RedisConfigTwo {
 
 
    @Value("${spring.redis2.host:127.0.0.1}")
    private String host;
    @Value("${spring.redis2.port:6379}")
    private int port;
    @Value("${spring.redis2.password:redis123}")
    private String password;
    @Value("${spring.redis2.timeout:6000}")
    private int timeout;
    @Value("${spring.redis2.database:0}")
    private int database;
    
    //pool映射
    @Value("${spring.redis2.lettuce.pool.max-active}")
    private int maxActive;
    @Value("${spring.redis2.lettuce.pool.max-idle}")
    private int maxIdle;
    @Value("${spring.redis2.lettuce.pool.min-idle}")
    private int minIdle;
    @Value("${spring.redis2.lettuce.pool.max-wait}")
    private long maxWait;
    
    
    
    
	public String getHost() {
		return host;
	}
	public void setHost(String host) {
		this.host = host;
	}
	public int getPort() {
		return port;
	}
	public void setPort(int port) {
		this.port = port;
	}
	public String getPassword() {
		return password;
	}
	public void setPassword(String password) {
		this.password = password;
	}
	public int getTimeout() {
		return timeout;
	}
	public void setTimeout(int timeout) {
		this.timeout = timeout;
	}
	public int getDatabase() {
		return database;
	}
	public void setDatabase(int database) {
		this.database = database;
	}
	public int getMaxActive() {
		return maxActive;
	}
	public void setMaxActive(int maxActive) {
		this.maxActive = maxActive;
	}
	public int getMaxIdle() {
		return maxIdle;
	}
	public void setMaxIdle(int maxIdle) {
		this.maxIdle = maxIdle;
	}
	public int getMinIdle() {
		return minIdle;
	}
	public void setMinIdle(int minIdle) {
		this.minIdle = minIdle;
	}
	public long getMaxWait() {
		return maxWait;
	}
	public void setMaxWait(long maxWait) {
		this.maxWait = maxWait;
	}
    
    
    
}
package com.example.two.config.redis;
 
import java.util.List;
 
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
 
import lombok.Data;
 
/**
 * 映射redis的哨兵配置配置
 * yml:
 
  #redis哨兵.一主2从192.168.10.1:6379,192.168.10.2:6379,192.168.10.3:6379。三哨兵192.168.10.1:26379,192.168.10.2:26379,192.168.10.3:26379
spring:  
  redis3:
    timeout: 6000ms
    database: 0 
    host: 192.168.10.1 #主节点的master
    password: ha@123 #redis密码
    port: 6379 #主节点的master端口
    lettuce:
      pool: 
        max-active: 1000 #连接池最大连接数(使用负值表示没有限制)
        max-idle: 10 #连接池中的最大空闲连接
        min-idle: 3 #连接池中的最小空闲连接
        max-wait: -1 #连接池最大阻塞等待时间(使用负值表示没有限制)
    sentinel: 
      master: mymaster 
      nodes: 
        - 192.168.10.1:26379
        - 192.168.10.2:26379
        - 192.168.10.3:26379
      
 * 
 * @author lsy
 *
 */
//@Data
@ConfigurationProperties(prefix="spring.redis3.sentinel")
public class RedisConfigThree {
 
    @Value("${spring.redis3.host:127.0.0.1}")
    private String host;
    @Value("${spring.redis3.port:6379}")
    private int port;
    @Value("${spring.redis3.password:redis123}")
    private String password;
    @Value("${spring.redis3.timeout:6000}")
    private int timeout;
    @Value("${spring.redis3.database:0}")
    private int database;
    
    //pool映射
    @Value("${spring.redis3.lettuce.pool.max-active}")
    private int maxActive;
    @Value("${spring.redis3.lettuce.pool.max-idle}")
    private int maxIdle;
    @Value("${spring.redis3.lettuce.pool.min-idle}")
    private int minIdle;
    @Value("${spring.redis3.lettuce.pool.max-wait}")
    private long maxWait;
    
    //setinel映射
    List<String> nodes;//@ConfigurationProperties(prefix="spring.redis3.sentinel")映射
    
    @Value("${spring.redis3.sentinel.master:mymaster}")
    private String master;
 
    
    
    
	public String getHost() {
		return host;
	}
 
	public void setHost(String host) {
		this.host = host;
	}
 
	public int getPort() {
		return port;
	}
 
	public void setPort(int port) {
		this.port = port;
	}
 
	public String getPassword() {
		return password;
	}
 
	public void setPassword(String password) {
		this.password = password;
	}
 
	public int getTimeout() {
		return timeout;
	}
 
	public void setTimeout(int timeout) {
		this.timeout = timeout;
	}
 
	public int getDatabase() {
		return database;
	}
 
	public void setDatabase(int database) {
		this.database = database;
	}
 
	public int getMaxActive() {
		return maxActive;
	}
 
	public void setMaxActive(int maxActive) {
		this.maxActive = maxActive;
	}
 
	public int getMaxIdle() {
		return maxIdle;
	}
 
	public void setMaxIdle(int maxIdle) {
		this.maxIdle = maxIdle;
	}
 
	public int getMinIdle() {
		return minIdle;
	}
 
	public void setMinIdle(int minIdle) {
		this.minIdle = minIdle;
	}
 
	public long getMaxWait() {
		return maxWait;
	}
 
	public void setMaxWait(long maxWait) {
		this.maxWait = maxWait;
	}
 
	public List<String> getNodes() {
		return nodes;
	}
 
	public void setNodes(List<String> nodes) {
		this.nodes = nodes;
	}
 
	public String getMaster() {
		return master;
	}
 
	public void setMaster(String master) {
		this.master = master;
	}
    
    
}

最后是总配置

package com.example.two.config.redis;
 
import java.util.ArrayList;
import java.util.List;
 
import org.apache.commons.pool2.impl.GenericObjectPoolConfig;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.data.redis.connection.RedisClusterConfiguration;
import org.springframework.data.redis.connection.RedisNode;
import org.springframework.data.redis.connection.RedisPassword;
import org.springframework.data.redis.connection.RedisSentinelConfiguration;
import org.springframework.data.redis.connection.RedisStandaloneConfiguration;
import org.springframework.data.redis.connection.lettuce.LettuceClientConfiguration;
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.connection.lettuce.LettucePoolingClientConfiguration;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
 
/**
 * redis多数据源配置类
 * 我用了3个数据源,分别是集群,单实例,哨兵。
 * 在工程中同时使用。如果你的数据源是多个,按照这里的例子,再配N套就行。
 * 
 * 第一个是集群,
 * 第二个是单实例
 * 第三个是哨兵。
 * 
 * @author lsy
 *
 */
@Configuration
public class RedisConfig {
 
	@Autowired
	RedisConfigOne redisConfigOne;//集群的配置,读取yml文件
	
	@Autowired
	RedisConfigTwo redisConfigTwo;//单实例的配置,读取yml文件
	
	@Autowired
	RedisConfigThree redisConfigThree;//哨兵的配置,读取yml文件
	
	/************集群的配置--start*******************/
	//读取pool配置
	@Bean
    public GenericObjectPoolConfig redisPool() {
		GenericObjectPoolConfig config = new GenericObjectPoolConfig();
		config.setMinIdle(redisConfigOne.getMaxIdle());
		config.setMaxIdle(redisConfigOne.getMaxIdle());
		config.setMaxTotal(redisConfigOne.getMaxActive());
		config.setMaxWaitMillis(redisConfigOne.getMaxWait());
        return config;
    }
	@Bean
    public RedisClusterConfiguration redisConfig() {//集群配置类
		RedisClusterConfiguration redisConfig = new RedisClusterConfiguration(redisConfigOne.getNodes());
		redisConfig.setMaxRedirects(redisConfigOne.getMaxRedirects());
		redisConfig.setPassword(RedisPassword.of(redisConfigOne.getPassword()));
        return redisConfig;
    }
	@Bean("factory")
    @Primary
    public LettuceConnectionFactory factory(@Qualifier("redisPool") GenericObjectPoolConfig config, 
    		@Qualifier("redisConfig") RedisClusterConfiguration redisConfig) {//注意传入的对象名和类型RedisClusterConfiguration
        LettuceClientConfiguration clientConfiguration = LettucePoolingClientConfiguration.builder().poolConfig(config).build();
        return new LettuceConnectionFactory(redisConfig, clientConfiguration);
    }
	
	/**
	 * 集群redis数据源
	 * 
	 * @param connectionFactory
	 * @return
	 */
	@Bean("redisTemplate")
    @Primary
    public RedisTemplate<String, Object> redisTemplate(@Qualifier("factory")LettuceConnectionFactory connectionFactory) {//注意传入的对象名
        RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(connectionFactory);
 
        //设置序列化器
        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
        GenericJackson2JsonRedisSerializer genericJackson2JsonRedisSerializer = new GenericJackson2JsonRedisSerializer();
        
        redisTemplate.setKeySerializer(stringRedisSerializer);
        redisTemplate.setValueSerializer(genericJackson2JsonRedisSerializer);
        redisTemplate.setHashKeySerializer(stringRedisSerializer);
        redisTemplate.setHashValueSerializer(genericJackson2JsonRedisSerializer);
        redisTemplate.afterPropertiesSet();
        
        return redisTemplate;
    }
	/************集群的配置--end*******************/
	
	
    /************单实例的配置--start*******************/
	//读取pool配置
	@Bean
    public GenericObjectPoolConfig redisPool2() {
		GenericObjectPoolConfig config = new GenericObjectPoolConfig();
		config.setMinIdle(redisConfigTwo.getMaxIdle());
		config.setMaxIdle(redisConfigTwo.getMaxIdle());
		config.setMaxTotal(redisConfigTwo.getMaxActive());
		config.setMaxWaitMillis(redisConfigTwo.getMaxWait());
        return config;
    }
	
	@Bean
    public RedisStandaloneConfiguration redisConfig2() {
		RedisStandaloneConfiguration redisConfig = new RedisStandaloneConfiguration(redisConfigTwo.getHost(),redisConfigTwo.getPort());
		redisConfig.setPassword(RedisPassword.of(redisConfigTwo.getPassword()));
		return redisConfig;
    }
	
	@Bean("factory2")
    public LettuceConnectionFactory factory2(@Qualifier("redisPool2") GenericObjectPoolConfig config, 
    		@Qualifier("redisConfig2") RedisStandaloneConfiguration redisConfig) {//注意传入的对象名和类型RedisStandaloneConfiguration
        LettuceClientConfiguration clientConfiguration = LettucePoolingClientConfiguration.builder().poolConfig(config).build();
        return new LettuceConnectionFactory(redisConfig, clientConfiguration);
    }
	
	
	/**
	 * 单实例redis数据源
	 * 
	 * @param connectionFactory
	 * @return
	 */
	@Bean("redisTemplate2")
    public RedisTemplate<String, Object> redisTemplate2(@Qualifier("factory2")LettuceConnectionFactory connectionFactory) {//注意传入的对象名
        RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(connectionFactory);
 
        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
        GenericJackson2JsonRedisSerializer genericJackson2JsonRedisSerializer = new GenericJackson2JsonRedisSerializer();
 
        //设置序列化器
        redisTemplate.setKeySerializer(stringRedisSerializer);
        redisTemplate.setValueSerializer(genericJackson2JsonRedisSerializer);
        redisTemplate.setHashKeySerializer(stringRedisSerializer);
        redisTemplate.setHashValueSerializer(genericJackson2JsonRedisSerializer);
        redisTemplate.afterPropertiesSet();
        
        return redisTemplate;
    }
	/************单实例的配置--end*******************/
	
	
	
    /************哨兵的配置--start*******************/
	//读取pool配置
	@Bean
    public GenericObjectPoolConfig redisPool3() {
		GenericObjectPoolConfig config = new GenericObjectPoolConfig();
		config.setMinIdle(redisConfigThree.getMaxIdle());
		config.setMaxIdle(redisConfigThree.getMaxIdle());
		config.setMaxTotal(redisConfigThree.getMaxActive());
		config.setMaxWaitMillis(redisConfigThree.getMaxWait());
        return config;
    }
	@Bean
    public RedisSentinelConfiguration redisConfig3() {//哨兵的节点要写代码组装到配置对象中
		RedisSentinelConfiguration redisConfig = new RedisSentinelConfiguration();
		redisConfig.sentinel(redisConfigThree.getHost(), redisConfigThree.getPort());
		redisConfig.setMaster(redisConfigThree.getMaster());
		redisConfig.setPassword(RedisPassword.of(redisConfigThree.getPassword()));
		if(redisConfigThree.getNodes()!=null) {
			List<RedisNode> sentinelNode=new ArrayList<RedisNode>();
			for(String sen : redisConfigThree.getNodes()) {
				String[] arr = sen.split(":");
				sentinelNode.add(new RedisNode(arr[0],Integer.parseInt(arr[1])));
			}
			redisConfig.setSentinels(sentinelNode);
		}
		return redisConfig;
    }
	@Bean("factory3")
    public LettuceConnectionFactory factory3(@Qualifier("redisPool3") GenericObjectPoolConfig config, 
    		@Qualifier("redisConfig3") RedisSentinelConfiguration redisConfig) {//注意传入的对象名和类型RedisSentinelConfiguration
        LettuceClientConfiguration clientConfiguration = LettucePoolingClientConfiguration.builder().poolConfig(config).build();
        return new LettuceConnectionFactory(redisConfig, clientConfiguration);
    }
	
	/**
	 * 哨兵redis数据源
	 * 
	 * @param connectionFactory
	 * @return
	 */
	@Bean("redisTemplate3")
    public RedisTemplate<String, Object> redisTemplate3(@Qualifier("factory3")LettuceConnectionFactory connectionFactory) {//注意传入的对象名
        RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(connectionFactory);
 
        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
        GenericJackson2JsonRedisSerializer genericJackson2JsonRedisSerializer = new GenericJackson2JsonRedisSerializer();
 
        //设置序列化器
        redisTemplate.setKeySerializer(stringRedisSerializer);
        redisTemplate.setValueSerializer(genericJackson2JsonRedisSerializer);
        redisTemplate.setHashKeySerializer(stringRedisSerializer);
        redisTemplate.setHashValueSerializer(genericJackson2JsonRedisSerializer);
        redisTemplate.afterPropertiesSet();
        
        return redisTemplate;
    }
	/************哨兵的配置--end*******************/
}

这样多数据源就配好了。按照这个例子可以进行其他各种多数据源的配置。

————————————————
版权声明:本文为CSDN博主「索隆」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/lushuaiyin/article/details/105516690

posted @ 2023-02-13 16:01  Zzzy君不见  阅读(1450)  评论(1编辑  收藏  举报