且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

Redis集群的一点一滴

更新时间:2021-07-03 23:25:28

本文并非介绍如何搭建一个集群,也不是介绍集群如何使用,重点是分享一些大家在使用集群过程中经常遇到的,经常提出来的问题:


问题一 Exception: Could not get resource from pool

   使用jedis客户端,无论缓存是以集群模式还是单点模式部署,凡是遇到这种问题,归结于无法从连接池中获取到连接,那么哪些原因导致获取链接失败呢?

   1.1 跨机房访问,注意网络是否可以访问,有无防火墙;

   1.2 本机访问,若redis以单机模式部署,注意是否启用密码认证;

   1.3 redis.conf配置bind是否绑定本地ip地址(建议绑定本地真实ip地址);

   1.4 若前置已部署代理,检查代理服务是否正常运行;

   1.5 最后必须保证redis服务正常运行,另外配置的ip与port都是正确的;


问题二 JedisRedirectionException: Too many cluster directions

   问题分析有两种异常造成:
   2.1 JedisMovedDataException:节点迁移后重新renew本地slot与redis节点的映射Map
   2.2 JedisAskDataException:数据正在迁移,发生asking问题, 获取asking的      Jedis,此过程最多循环redirections次。
   这种异常说明重定向redirections次,仍然没有找到可以处理的节点来完成本次redis操作。原因主要包括但不限于以下几点:
     1. 压测遇到的超时比较多,默认超时时间是2000ms
       1.1 网络原因:比如是否存在跨机房、网络闪断等。
       1.2 存在慢查询的操作,因为redis是单线程,如果有慢查询的话,会阻塞后续操作。
       1.3 value值过大(如二进制流),可能性非常小
       1.4 aof文件正在重写,rdb文件或 aof文件正在fork进程
    2. 节点之间槽位发生变化,会发生JedisMovedDataException
    3. 节点之间发生数据迁移,会发生JedisAskDataException


问题三 ASK转向与MOVED转向区别及场景介绍

   MOVED转向通常发生在集群稳定状态下:若向node-1节点发送key1请求,经过CRC算法计算出key1的slot值,若slot值属于node-1节点的处理范围则直接处理,若不属于node-1节点的处理范围则返回moved异常和能够处理该slot的节点信息(格式:-MOVED SLOT IP:PORT),注:集群中每个节点都记录其他节点的信息。客户端的实现会根据返回的-MOVED转向来将请求再次转发到正确的节点处理。若集群slot不断地发生迁移,那么客户端会不断地根据服务端返回的-MOVED转向重新转发。


   ASK转向通常发生在集群slot迁移过程中:若集群正在发生slot迁移,slot迁移实质上是迁移slot中每一个key的过程,若key1经过计算slot值后路由到node-1发现slot正在发生迁移,而且该key位置已经迁移到node-2,同时这次迁移过程并没有结束(即仍然有key存在于node-1中),那么返回给客户端ASK转向。客户端根据ASK转向将key1转发到node-2中,注意这次转发是基于请求的临时转发,下次请求key2依然根据CRC算法计算slot值若位于node-1将继续转发请求到node-1。若迁移过程结束,所有的key请求经过计算slot值永久的路由到实际的目标节点。


问题四 集群通信方式以及选举过程介绍

   集群节点通过gossip协议进行互相关注(ping),若集群发现某个节点长期没有收到(+pong)响应,那么会每秒一次进行跟踪疑似下线的节点。选举是通过raft算法进行选举,选举过程不予介绍。重点介绍集群在选举过程中可能存在的问题:若master节点跟随的slave节点比较多的话,那么选举的过程耗时略微长一点。那么在这个过程中,所有被路由到这个节点处理的请求均抛出异常。


5. 集群不支持的功能大汇总

   5.1 事务,不管是数据库还是缓存跨节点的事务很棘手

   5.2 Pipeline,队列命令涉及到命令的分发和结果聚合

   5.3 密码认证,多节点认证比较难以协调

   5.4 mget/mset,多命令操作涉及到命令分发与聚合

   5.5 涉及到multi-key的操作或者跨节点的操作均不支持


6. 停机数据备份或迁移简单方案介绍

   不少网友问到数据迁移,如跨级房迁移,或者select 1迁移至select 0,这样的场景最简便的方案是备份物理文件拷贝过去,注意若将select 1迁移到select 0,只需要将aof文件中的select 1改成select 0,redis服务启动默认优先通过aof来恢复数据的。


7. 是否有必要开启rdb或者aof备份

   开启rdb,aof的好处就是备份,主从复制,最新的redis已经支持diskless的发送复制流(即无需将复制的信息写入磁盘而是直接发送给slave节点,见redis.conf参数repl-diskless-sync),当然这个功能现在使用的也很少,风险比较大。那么开启rdb,aof的缺点,fork进程,作者使用高压测试,发现后台fork进程复制的速度是比较慢的,起码肉眼能看到。



。。。待完善。。。