前置redis单例基本搭建参考博客:redis基础服务搭建
redis集群主要修改配置:主从复制
1. 主机配置
复制一份redis.conf成redis-6379.conf。修改配置:
```
#演示方便,开放ip连接
bind 0.0.0.0
#后台运行
daemonize yes
#pid文件
pidfile /var/run/redis_6379.pid
#日志文件
logfile "6379.log"
```
2. 从机配置
复制一份redis.conf成redis-6380.conf。修改配置:
```
#设置所有ip都可访问
bind 0.0.0.0
#端口
port 6380
#是否后台方式启动
daemonize yes
#每个服务一个pid,存放地址
pidfile /var/run/redis_6380.pid
#日志文件设置
logfile "6380.log"
#slaveof表示作为从库的配置,设置主库地址端口(主写从复制读)
slaveof 127.0.0.1 6379
#主库密码(没有设置不用写)
requirepass 654321
#从库只能读不能写(主从配置)
slave-read-only yes
#单台服务器做集群需要修改,名称不能一致
dbfilename dump-6379.rdb
```
3. 启动服务(进入redis根目录)执行命令:我这里文件名为redis-6379.conf、redis-6380.conf、redis-6381.conf存放在根目录
```
[root@VM_235_253_centos redis-4.0.9]# ./src/redis-server redis-6379.conf
[root@VM_235_253_centos redis-4.0.9]# ./src/redis-server redis-6380.conf
[root@VM_235_253_centos redis-4.0.9]# ./src/redis-server redis-6381.conf
```
4. 查看redis的信息 查看redis的信息
主库信息
```
[root@VM_235_253_centos redis-4.0.9]# ./src/redis-cli -p 6379 -a 654321 info replication# Replication
```
其中-p 6379表示指定端口
-a 654321表示指定端口的密码,没有可以不加此参数
replication表示主从的信息
```
# Replication
#主库
role:master
#2从库
connected_slaves:2
slave0:ip=119.29.76.169,port=6381,state=online,offset=207209,lag=1
slave1:ip=119.29.76.169,port=6380,state=online,offset=207209,lag=1
master_replid:59f3ac708c36d91887f61d92d48a0ea8ac397fe5
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:207209
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:207209
```
查看6380从库信息
```
[root@VM_235_253_centos redis-4.0.9]# ./src/redis-cli -p 6380 -a 654321 info replication
# Replication
#从库
role:slave
#主库地址
master_host:119.29.76.169
#主库端口
master_port:6379
master_link_status:up
master_last_io_seconds_ago:1
master_sync_in_progress:0
slave_repl_offset:233021
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:59f3ac708c36d91887f61d92d48a0ea8ac397fe5
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:233021
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:233021
```
配置哨兵:
- 复制根目录下sentinel.conf配置文件
- 修改主要配置
#设置哨兵服务端口
port 26379
#设置后台启动
daemonize yes
#文件地址存放地址
dir /opt/redis-4.0.11/data
#Sentinel去监视一个名为mymaster 的主redis实例,这个主实例的IP地址为本机地址127.0.0.1,端口号为6379,而将这个主实例判断为失效至少需要2个 Sentinel进程的同意,只要同意Sentinel的数量不达标,自动failover就不会执行
sentinel monitor mymaster 127.0.0.1 6379 2
#设置连接master和slave时的密码,注意的是sentinel不能分别为master和slave设置不同的密码,因此master和slave的密码应该设置相同。
# sentinel auth-pass <master-name> <password>
#指定了Sentinel认为Redis实例已经失效所需的毫秒数。当实例超过该时间没有返回PING,或者直接返回错误,那么Sentinel将这个实例标记为主观下线。只有一个 Sentinel进程将实例标记为主观下线并不一定会引起实例的自动故障迁移:只有在足够数量的Sentinel都将一个实例标记为主观下线之后,实例才会被标记为客观下线,这时自动故障迁移才会执行
sentinel down-after-milliseconds mymaster 30000
#指定了在执行故障转移时,最多可以有多少个从Redis实例在同步新的主实例,在从Redis实例较多的情况下这个数字越小,同步的时间越长,完成故障转移所需的时间就越长
sentinel parallel-syncs mymaster 1
#如果在该时间(ms)内未能完成failover操作,则认为该failover失败
sentinel failover-timeout mymaster 180000
#指定sentinel检测到该监控的redis实例指向的实例异常时,调用的报警脚本。该配置项可选,但是很常用
# sentinel notification-script <master-name> <script-path>
启动哨兵:两个配置文件在根目录分别为sentinel-26379.conf、sentinel-26380.conf
``` [root@VM_235_253_centos redis-4.0.9]# ./src/redis-sentinel sentinel-26379.conf [root@VM_235_253_centos redis-4.0.9]# ./src/redis-sentinel sentinel-26380.conf ```
Spring boot 配置:
- 引入redis包
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
- application.yml Spring配置
spring:
redis:
#有密码则需要设置
password: 654321
#这里只需要配置哨兵即可
sentinel:
master: mymaster
nodes: 119.xx.xx.xxx:26379,119.xx.xx.xxx:26380
- redis序列化
/**
* redis序列化配置
* @author 50238
*/
@Configuration
public class RedisConfig {
/**
* redisTemplate 序列化使用的jdkSerializeable, 存储二进制字节码, 所以自定义序列化类
*
* @param redisConnectionFactory
* @return
*/
@Bean
public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
RedisTemplate<Object, Object> redisTemplate = new RedisTemplate<>();
redisTemplate.setConnectionFactory(redisConnectionFactory);
// 使用Jackson2JsonRedisSerialize 替换默认序列化
Jackson2JsonRedisSerializer<Object> jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer<>(Object.class);
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
objectMapper.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
jackson2JsonRedisSerializer.setObjectMapper(objectMapper);
// 设置value的序列化规则和 key的序列化规则
redisTemplate.setKeySerializer(new StringRedisSerializer());
redisTemplate.setValueSerializer(jackson2JsonRedisSerializer);
redisTemplate.afterPropertiesSet();
return redisTemplate;
}
}
最后测试代码:
@RunWith(SpringRunner.class)
@SpringBootTest
public class BlogApplicationTests {
@Autowired
private RedisTemplate redisTemplate;
@Test
public void contextLoads() {
ValueOperations valueOperations = redisTemplate.opsForValue();
valueOperations.set("open", "String");
System.out.println(valueOperations.get("open"));
}
}
使用redis工具也可以看到确实主从做了复制,复制信息等可以从redis日志中也可以看到。
Redis哨兵-实现Redis高可用