redis的哨兵和cluster在java代码中的配置

1.哨兵:
applicationContext.xml:

<!-- redis sentinel 配置 -->
	<bean id="poolConfig" class="redis.clients.jedis.JedisPoolConfig">  
        <property name="maxTotal" value="${im.hs.server.redis.maxTotal}" />  
        <property name="minIdle" value="${im.hs.server.redis.minIdle}" />  
        <property name="maxWaitMillis" value="${im.hs.server.redis.maxWaitTime}" />  
        <property name="maxIdle" value="${im.hs.server.redis.maxIdle}" />  
        <property name="testOnBorrow" value="${im.hs.server.redis.testOnBorrow}" />  
        <property name="testOnReturn" value="true" />  
        <property name="testWhileIdle" value="true" />  
    </bean>  
  
    <bean id="sentinelConfiguration"  
        class="org.springframework.data.redis.connection.RedisSentinelConfiguration">  
        <property name="master">  
            <bean class="org.springframework.data.redis.connection.RedisNode">  
                <property name="name" value="${im.hs.server.redis.sentinel.masterName}"></property>  
            </bean>  
        </property>  
        <property name="sentinels">  
            <set>  
                <bean class="org.springframework.data.redis.connection.RedisNode">  
                    <constructor-arg name="host"  
                        value="${im.hs.server.redis.sentinel1.host}"></constructor-arg>  
                    <constructor-arg name="port"  
                        value="${im.hs.server.redis.sentinel1.port}"></constructor-arg>  
                </bean>  
                <bean class="org.springframework.data.redis.connection.RedisNode">  
                    <constructor-arg name="host"  
                        value="${im.hs.server.redis.sentinel2.host}"></constructor-arg>  
                    <constructor-arg name="port"  
                        value="${im.hs.server.redis.sentinel2.port}"></constructor-arg>  
                </bean>  
                <bean class="org.springframework.data.redis.connection.RedisNode">  
                    <constructor-arg name="host"  
                        value="${im.hs.server.redis.sentinel3.host}"></constructor-arg>  
                    <constructor-arg name="port"  
                        value="${im.hs.server.redis.sentinel3.port}"></constructor-arg>  
                </bean>  
            </set>  
        </property>  
    </bean>  
  
    <bean id="sentinelConnectionFactory"  
        class="org.springframework.data.redis.connection.jedis.JedisConnectionFactory">  
        <property name="password" value="${im.hs.server.redis.sentinel.password}"></property> 
        <constructor-arg name="sentinelConfig" ref="sentinelConfiguration"></constructor-arg>  
        <constructor-arg name="poolConfig" ref="poolConfig"></constructor-arg>  
    </bean>
	<!-- redis sentinel 配置结束 -->

redis-sentinel.properties:

# Redis settings  
#sentinel1的IP和端口  
im.hs.server.redis.sentinel1.host=192.168.126.131
im.hs.server.redis.sentinel1.port=26379
#sentinel2的IP和端口  
im.hs.server.redis.sentinel2.host=192.168.126.132
im.hs.server.redis.sentinel2.port=26380
#sentinel3的IP和端口  
im.hs.server.redis.sentinel3.host=192.168.126.133
im.hs.server.redis.sentinel3.port=26381
#sentinel的鉴权密码  
im.hs.server.redis.sentinel.masterName=mymaster
im.hs.server.redis.sentinel.password=12345678
#最大闲置连接数  
im.hs.server.redis.maxIdle=500
#最大连接数,超过此连接时操作redis会报错  
im.hs.server.redis.maxTotal=5000
im.hs.server.redis.maxWaitTime=1000
im.hs.server.redis.testOnBorrow=true
#最小闲置连接数,spring启动的时候自动建立该数目的连接供应用程序使用,不够的时候会申请。  
im.hs.server.redis.minIdle=300

测试:

package com.shidebin.mongodb.spring_redis;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.DefaultTypedTuple;
import org.springframework.data.redis.core.HashOperations;
import org.springframework.data.redis.core.ListOperations;
import org.springframework.data.redis.core.SetOperations;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.data.redis.core.ZSetOperations;
import org.springframework.data.redis.core.ZSetOperations.TypedTuple;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.util.CollectionUtils;

import com.alibaba.fastjson.JSON;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
public class RedisSentinelTest {
	@Autowired
	public ValueOperations<String,String> stringRedisTemplate;
	@Autowired
	public HashOperations<String,String,String> hashRedisTemplate;
	@Autowired
	public ListOperations<String,String> listRedisTemplate;
	@Autowired
	public SetOperations<String,String> setRedisTemplate;
	@Autowired
	public ZSetOperations<String,String> zSetRedisTemplate;
	@Test
	public void set() {
		//set name shidebin
		stringRedisTemplate.set("name", "shidebin");	
		//保存对象
		User user = User.getUserBuilder().name("shidebin").age(29).sex("男").build();
		String jsonString = JSON.toJSONString(user);
		stringRedisTemplate.set("user:1", jsonString);
		//保存list
		List<String> list = new ArrayList<String>();
		list.add("aaa");
		list.add("bbb");
		list.add("ccc");
		String listJson = JSON.toJSONString(list);
		stringRedisTemplate.set("list", listJson);
		//保存map
		Map<String,String> map = new HashMap<String,String>();
		map.put("name", "shidebin");
		map.put("age", "29");
		map.put("phone", "18615412359");
		String mapJson = JSON.toJSONString(map);
		stringRedisTemplate.set("map", mapJson);
		//mset country china city beijing
		stringRedisTemplate.multiSet(map);
	}
	@SuppressWarnings("unchecked")
	@Test
	public void get() {
		//取string
		String name = stringRedisTemplate.get("name");
		System.out.println(name);
		//取对象
		String userStr = stringRedisTemplate.get("user:1");
		User parseObject = JSON.parseObject(userStr, User.class);
		System.out.println(userStr);
		System.out.println(parseObject);
		//取list
		String listStr = stringRedisTemplate.get("list");
		List<String> parseObject2 = JSON.parseArray(listStr, String.class);
		System.out.println(listStr);
		System.out.println(parseObject2);
		//取map
		String mapStr = stringRedisTemplate.get("map");
		Map<String,String> parseObject3 = JSON.parseObject(mapStr, Map.class);
		System.out.println(mapStr);
		System.out.println(parseObject3);
		//mget country city address
		List<String> multiGet = stringRedisTemplate.multiGet(Arrays.asList("name","age","phone"));
		System.out.println(multiGet);
	}
	//hash
	@Test
	public void hSet() {
		Map<String,String> map = new HashMap<String,String>();
		map.put("name", "shidebin");
		map.put("age", "29");
		map.put("phone", "18615412359");
		hashRedisTemplate.putAll("user:2", map);
	}
	@Test
	public void hGet() {
		Map<String, String> entries = hashRedisTemplate.entries("user:2");
		System.out.println(entries);
	}
	//list
	@Test
	public void lpush() {
		List<String> list = new ArrayList<String>();
		list.add("aaa");
		list.add("bbb");
		list.add("ccc");
		listRedisTemplate.leftPushAll("list:1", list);
	}
	@Test
	public void lget() {
		List<String> range = listRedisTemplate.range("list:1", 0, -1);
		System.out.println(range);
	}
	//list
		@Test
		public void sset() {
			List<String> list = new ArrayList<String>();
			list.add("aaa");
			list.add("bbb");
			list.add("ccc");
			setRedisTemplate.add("set:1", list.toArray(new String[] {}));
		}
		@Test
		public void sget() {
			Set<String> members = setRedisTemplate.members("set:1");
			System.out.println(members);
		}
		//list
		@Test
		public void zpush() {
			Set<TypedTuple<String>> set = new HashSet<TypedTuple<String>>();
			TypedTuple<String> tt = new DefaultTypedTuple<String>("shidebin",Double.valueOf(23));
			set.add(tt);
			zSetRedisTemplate.add("zset",set);
		}
		@Test
		public void zget() {
			Set<TypedTuple<String>> rangeWithScores = zSetRedisTemplate.rangeWithScores("zset", 0, -1);
			rangeWithScores.stream().forEach(action -> {
				System.out.println(action.getScore());
				System.out.println(action.getValue());
			});
		}
}

cluster配置:
applicationContext.xml:

<!-- cluster 集群配置 -->
	 <bean id="genericObjectPoolConfig" class="org.apache.commons.pool2.impl.GenericObjectPoolConfig">
        <property name="maxTotal" value="${maxTotal}" />
        <property name="minIdle" value="${minIdle}" />
        <property name="maxIdle" value="${maxIdle}" />
        <property name="maxWaitMillis" value="${maxWaitMillis}" />
        <property name="testOnBorrow" value="${testOnBorrow}" />
    </bean>
	<bean id="jedisCluster" class="com.shidebin.mongodb.spring_redis.JedisClusterFactory">
        <property name="addressConfig" value="classpath:redis-cluster.properties"/>
        <property name="addressKeyPrefix" value="address" />
        <property name="timeout" value="${timeout}" />
        <!--代表集群有几台redis-->
        <property name="maxRedirections" value="${maxRedirections}" />
        <property name="genericObjectPoolConfig" ref="genericObjectPoolConfig" />
    </bean>
	<!-- redis cluster 集群配置结束 -->

redis_cluster.properties:

address1=192.168.126.128:6379
address2=192.168.126.129:6380
address3=192.168.126.130:6381
address4=192.168.126.131:6389
address5=192.168.126.132:6390
address6=192.168.126.133:6391
#最大连接数
maxTotal=1024
#客户端超时时间单位是毫秒
timeout=300000
#最大连接数
maxActive=1024
#最小空闲数
minIdle=8
#最大空闲数
maxIdle=100
#最大建立连接等待时间
maxWaitMillis=1000
#redis集群单位数
maxRedirections=6
testOnBorrow=true

JedisClusterFactory类:

package com.shidebin.mongodb.spring_redis;

import java.io.IOException;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Properties;
import java.util.Set;
import java.util.regex.Pattern;

import org.apache.commons.pool2.impl.GenericObjectPoolConfig;
import org.springframework.beans.factory.FactoryBean;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.core.io.Resource;

import redis.clients.jedis.HostAndPort;
import redis.clients.jedis.JedisCluster;

public class JedisClusterFactory implements InitializingBean{
	private Resource addressConfig;
	private String addressKeyPrefix;
	private JedisCluster jedisCluster;
	private Integer timeout;
	private Integer maxRedirections;
	private GenericObjectPoolConfig genericObjectPoolConfig;
	private Pattern p = Pattern.compile("^.+[:]\\d{1,5}\\s*$");
	@Override
	public void afterPropertiesSet() throws Exception {
		Set<HostAndPort> nodes = getNodes();
		this.jedisCluster = new JedisCluster(nodes,timeout,maxRedirections,genericObjectPoolConfig);
	}
	private Set<HostAndPort> getNodes(){
		Set<HostAndPort> nodes = new HashSet<HostAndPort>();
		Properties source = new Properties();
		try {
			source.load(this.addressConfig.getInputStream());
			for(Iterator<Object> ite = source.keySet().iterator();ite.hasNext();){
				String key = ite.next().toString();
				if(key.startsWith(addressKeyPrefix)) {
					String val = source.getProperty(key);
					boolean isAddress = p.matcher(val).matches();
					if(!isAddress) {
						throw new IllegalArgumentException("cluster 地址格式不对");
					}
					HostAndPort hap = new HostAndPort(val.split(":")[0],Integer.parseInt(val.split(":")[1]));
					nodes.add(hap);
				}
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
		return nodes;
	}
	public void setAddressConfig(Resource addressConfig) {
		this.addressConfig = addressConfig;
	}
	public void setAddressKeyPrefix(String addressKeyPrefix) {
		this.addressKeyPrefix = addressKeyPrefix;
	}
	public void setTimeout(Integer timeout) {
		this.timeout = timeout;
	}
	public void setMaxRedirections(Integer maxRedirections) {
		this.maxRedirections = maxRedirections;
	}
	public void setGenericObjectPoolConfig(GenericObjectPoolConfig genericObjectPoolConfig) {
		this.genericObjectPoolConfig = genericObjectPoolConfig;
	}
	public JedisCluster getJedisCluster() {
		return jedisCluster;
	}
	
}

JedisCluster实例也可以通过FactoryBean来实现,此类直接用了get()方法,目前不清楚俩种方法的优劣,目测get()更为简便。
测试:

package com.shidebin.mongodb.spring_redis;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import redis.clients.jedis.JedisCluster;



@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
public class RedisClusterTest {
	 @Autowired
	 JedisClusterFactory jf;
	 @Test
	 public void testCluster() {
		 JedisCluster jedisCluster = jf.getJedisCluster();
		 String set = jedisCluster.set("abd".getBytes(), "fasdfjklasd".getBytes());
		 System.out.println(set);
	 }
	 
}

git上工程地址:https://github.com/shidebin/redis/tree/master/spring-redis

哨兵模式是Redis高可用解决方案的一部分,它通过一组哨兵服务器监控主服务器,并在主节点故障时自动切换到从节点成为新的主节点。在Spring Boot应用集成Redis哨兵,可以提供可靠的数据持久化和故障恢复。 以下是配置Spring Boot应用使用Redis哨兵的基本步骤: 1. 添加依赖:首先,在项目的pom.xml或build.gradle文件添加Spring Data Redis和 lettuce-clusterRedis客户端支持哨兵)的依赖: Maven: ```xml <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-redis</artifactId> </dependency> <dependency> <groupId>io.lettuce</groupId> <artifactId>lettuce-core</artifactId> </dependency> ``` Gradle: ```groovy implementation 'org.springframework.boot:spring-boot-starter-data-redis' implementation 'io.lettuce:lettuce-core' ``` 2. 配置RedisSentinelConfiguration:创建一个@Configuration类并注入`@EnableCaching`和`@EnableRedisHttpSession`,然后覆盖`redisTemplate` bean以指向哨兵集群: ```java import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.data.redis.connection.RedisConnectionFactory; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.data.redis.sentinel.RedisSentinelConfiguration; import org.springframework.data.redis.sentinel.SentinelConnectionProvider; @Configuration @EnableCaching @EnableRedisHttpSession public class RedisConfig { @Autowired private SentinelConnectionProvider connectionProvider; @Bean(name = "sentinelRedisConnectionFactory") public RedisConnectionFactory sentinelConnectionFactory() { RedisSentinelConfiguration config = new RedisSentinelConfiguration() .master("yourMasterName") // 根据实际情况替换为主机名 .sentinels(connectionProvider.getSentinels()); // 获取所有哨兵实例 return new LettuceConnectionFactory(config); } @Bean(name = "redisTemplate") public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory factory) { RedisTemplate<String, Object> template = new RedisTemplate<>(); template.setConnectionFactory(factory); return template; } } ``` 记得将`yourMasterName`替换为你实际的主节点名称。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值