Redis心得

本文详细介绍Redis三种集群模式:主从、哨兵和集群,并重点讲解如何搭建Redis集群,包括配置、启动、验证、水平扩容、删除节点等步骤。
redis三种集群模式:
1.主从(相当于读写分离,主机存在单点故障的问题)
2.哨兵(相当于在主从的基础上增加了一台哨兵服务器,当主节点宕机后,哨兵会从剩余从服务器中选出一台成为主节点,当原先的主节点恢复后,该主节点会成为从节点,但是无法做数据分片)
3.集群(redis3.0版本以后出的,相当于多套主从形成集群,可以做数据分片,通过redis的hash槽,数据可移植,可以水平增减节点)

redis与memcached的特性不同,redis并不是靠单点的服务器体现特性,redis倾向于多实例,因为其单点是串行执行的,redis什么时候比较慢,当为了保证数据的高可用,开启AOF的时候,会大大降低写的速度,因为会记录日志,慢了怎么办呢?多增加节点,分担压力

而memcached更倾向于单点,并行执行

如何解决高并发?
前端入口处可以用Nginx,甚至集群,每个模块可以有单独的域名,比如购物车和商品之间,做流量控制,
而最终的瓶颈一定在后台服务器数据库,mysql的主从复制,或者像NoSql技术作缓存

Nosql中的数据不能要求强一致性,如果一定要求,那么一定要在mysql中存一份数据,再存入redis,每次更新两份,但是两种数据库又要保证事务一致性,代码层面的解决可以用try/catch。 

redis之所以有16个数据库主要是因为2.0的时候没有集群的概念,为了实现数据的安全以及大数据量,可以用16个数据库做数据的备份以及分片。

redis的事务是不太完善的

redis持久化机制

redis是一个支持持久化的内存数据库,也就是说redis需要经常将内存中的数据同步到磁盘来保证数据持久化。

redis持久化的两种方式:

1 snapshotting快照的方式(默认):将内存中的数据已快照的方式写入二进制文件中,默认为dump.rdb,可以通过配置设置自动进行快照持久化的方式:

snapshotting:

    save  900  1:900秒内如果1个key被修改,则发起快照保存
    save  300  10:300面内如果有10个key被修改,则发起快照保存

    save  60  10000:60秒内如果有10000个key被修改,则发起快照保存。

2 append-only-file(aof)的方式:有点类似于oracle的undo日志,由于快照方式是在一定时间做一次,所以可能发生redis意外down的情况就丢失redis最后一次快照的所有修改的数据,aof比快照方式有更好的持久化性,是由于在使用aof时,redis会将每一个收到的写命令都通过write函数追加到命令中,当redis重新启动时,会重新执行文件中保存的写命令来在内存中重建数据库的内容。这个文件在bin目录下:appendonly.aof,aof不是立即写到硬盘上,可以通过配置文件强行写到硬盘中。

aof设置:

appendonly  yes:启动aof持久化方式  有三种修改方式:
appendfsync  always:收到写命令就立即写入到磁盘,效率最慢,但是保证完全的持久化(对于实际项目中,如果不希望数据丢失,都会选用这种)
appendfsync  everysec:每秒钟写入磁盘一次,在性能和持久化方面做了很好的折中(redis的性能很高,甚至可以支持到每秒钟几十万次的写操作,所以在高并发下宕机时影响也是不小)

appendfsync  no:完全依赖os(系统性能),性能最好,持久化没保证

redis集群搭建

集群搭建:至少要三个master

第一步:创建一个文件夹redis-cluster,然后在其下创建6个文件夹
1 mkdir  -p  /usr/local/redis-cluster

2 mkdir 7001 mkdir 7002 mkdir 7003 mkdir 7004 mkdir 7005 mkdir 7006

第二步:把之前的redis.conf文件分别拷贝到700*文件夹下,修改700*下每个redis.conf文件:

(1)daemonize yes
(2)port  700*
(3)bind 192.168.25.129 (必须要绑定当前机器的IP,如果不绑定当使用jedis时可能会重定向很多次,也无法连接到redis服务器集群,set和get值时可能会等待很久,深坑误入
(4)dir  /usr/local/redis-cluster/700*/(指定数据文件存放位置,必须要指定不同的目录位置,不然会丢失数据,深坑勿入

(5)cluster-enabled  yes (启动集群模式)
(6)cluster-config-file  nodes700*.conf(这里的700*最好和端口号对应上,每一个节点对应的配置文件,在当前集群中,让集群知道当前节点的存在)
(7)cluster-node-timeout  5000

(8)appendonly  yes

第三步:把修改后的配置文件,分别copy到各个文件夹下,注意每个文件要修改端口号,并且nodes文件也要不相同。

第四步:由于reids集群需要使用ruby命令,所以我们需要安装ruby
(1)yum  install  ruby
(2)yum  install  rubygems

(3)gem  install  redis(安装reids和ruby的接口)(执行时出了bug:ERROR:  Error installing redis:
        redis requires Ruby version >= 2.2.2.)

查了资料发现是Centos默认支持ruby到2.0.0,可gem 安装redis需要最低是2.2.2

解决办法是 先安装rvm,再把ruby版本提升至2.3.3

1.安装curl

sudo yum install curl

2. 安装RVM

curl -L get.rvm.io | bash -s stable 

3.进入archives目录,解压rvm-1.29.3.tgz,安装之
cd /usr/local/rvm/archives

tar -zxf rvm-1.29.3.tgz
cd rvm-1.29.3
./install 
source /usr/local/rvm/scripts/rv m

4. 查看rvm库中已知的ruby版本

rvm list known

5. 安装一个ruby版本

rvm install 2.3.3

6. 使用一个ruby版本,设置默认版本

rvm use 2.3.3

7. 卸载一个已知版本

rvm remove 2.0.0

8. 查看ruby版本

ruby --version

9. 再安装redis就可以了

gem install redis

第五步:分别启动6个reids实例,然后检查是否启动成功
(1)./redis-server  redis.conf

(2)ps -el|grep redis  查看是否启动成功

第六步:首先到reids3.0的安装目录下,然后执行redis-trib.rb的命令
(1)cd  /usr/local/redis3.0/src

(2)./redis-trib.rb  create  --replicas  1 
192.168.25.129:7001 192.168.25.129:7002 192.168.25.129:7003 192.168.25.129:7004 192.168.25.129:7005  192.168.25.129:7006


第七步:集群搭建成功,进行验证:

(1)连接任意一个客户端即可:./redis-cli  -c  -h  -p(-c表示集群模式,-h  IP ,-p 端口号),如: ./redis-cli -c -h 192.168.25.129 -p 7001
(2)进行验证:cluster  info(查看集群信息),cluster  nodes(查看节点列表)
(3)进行数据操作
(4)关闭进群需要逐个关闭,使用命令:
 ./redis-cli -c -h 192.168.25.129 -p 700* shutdown

第八步:(补充)
友情提示:当出现集群无法启动时,删除临时的数据文件,再次重新启动每个reids服务,然后重新构造集群环境。

为redis中添加节点

1 首先创建文件夹,并复制配置文件到文件夹

修改配置文件内容:
cluster-config-file nodes-700*.conf
port 700*
dir /usr/local/redis-cluster/700*/

在vim中使用  %/s/新串/旧串/g  就可以替换

2 启动新加入的服务器

3 进入redis的安装包中

使用/redis-trib.rb ,执行命令./redis-trib.rb add-node 192.168.25.129:7007 192.168.25.129:7001,将新加入节点通知集群中任意一台节点



进入reids集群中,通过命令:cluster nodes,查询集群中节点发现节点已经被加入,但是并没有被分配hash槽

4 数据重新分片,这个时候需要使用reshard参数,通知集群中任意一台服务器
./redis-trib.rb reshard 192.168.25.129:7001

回到集群服务器中,查看现在各个服务器状态,服务器已处于运行状态并已经分配了hash槽


同理启动7008,服务器也将7008分为了主节点,而我们需要的是7008做7007的备份


登陆7008:./redis-cli -c -h 192.168.25.129 -p 7008

这样就实现了在集群启动的情况下,水平扩容,而且做到并不影响业务的同步执行。

删除节点

删除从节点 

 . /redis-trib.rb  del-node  ip:port   节点ID


7008节点已经消失

最后一步:尝试删除7007主节点,这个步骤会相对麻烦一些,因为主节点中已经分配了slot槽,所以我们必须先把7007里的slot槽放入到其他主节点中去,然后再进行移除节点操作,不然会出现数据丢失问题。

(1)删除7007节点之前,将全部slot槽移动到其他节点上去(目前只能把master的数据迁移到一个节点上),暂时做不了平均分配功能。 
执行命令: . /redis-trib.rb reshard 192.168.25.129:7007

(2)将节点全部转移后,slot槽已经为空

就可以按照上面删除slave的步骤删除主节点7007了

温馨提示:

1  在增加节点,重新分配slot槽时出现了bug

/usr/lib/ruby/gems/1.8/gems/redis-3.0.7/lib/redis/client.rb:97:in `call': ERR Slot 5462 is already busy (Redis::CommandError)
from /usr/lib/ruby/gems/1.8/gems/redis-3.0.7/lib/redis.rb:2432:in `method_missing'
from /usr/lib/ruby/gems/1.8/gems/redis-3.0.7/lib/redis.rb:37:in `synchronize'
from /usr/lib/ruby/1.8/monitor.rb:242:in `mon_synchronize'
from /usr/lib/ruby/gems/1.8/gems/redis-3.0.7/lib/redis.rb:37:in `synchronize'
from /usr/lib/ruby/gems/1.8/gems/redis-3.0.7/lib/redis.rb:2431:in `method_missing'
from ./redis-trib.rb:203:in `flush_node_config'
from ./redis-trib.rb:571:in `flush_nodes_config'
from ./redis-trib.rb:570:in `each'
from ./redis-trib.rb:570:in `flush_nodes_config'
from ./redis-trib.rb:820:in `create_cluster_cmd'
from ./redis-trib.rb:1026:in `send'

from ./redis-trib.rb:1026

经检查,这是由于上一次配置集群失败时留下的配置信息导致的。 只要把redis.conf中定义的 cluster-config-file 所在的文件删除,重新启动redis-server及执行命令:  ./redis-trib.rb   fix   ip:port  重新分配信息即可,如果还是不行就删除所有临时的数据文件,再次重新启动每个reids服务,然后重新构造集群环境。

在将删除的节点重新添加回集群时,出现error:[ERR] Node 192.168.25.129:7007 is not empty. Either the node already knows other nodes (check with CLUSTER NODES) or contains some key in database 0.
提示:该节点不是空的,要么他已经知道了其他节点,要么他的数据库不为空。

这种情况直接将这个原来已经被添加过的节点的nodes-*.conf文件删掉即可


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值