• 【Redis】记录一次K8S存储故障导致Redis集群拓扑异常的修复过程


    背景

    集群部署在K8S环境内,存储使用的localpv,有一台K8S主机节点磁盘故障,导致在该节点上的redis节点均出现故障,主要表现为持久化失败、集群拓扑异常,持久化失败可以临时关闭RDB和AOF持久化、等挂载好新的硬盘后,重新创建pvc进行恢复,经过观察,这些redis节点恢复后,operator并不能完成集群自愈,需要手动干预,主要表现为:集群拓扑异常:故障的节点没有被清理掉、新的节点没有以正常的角色加入到集群中。

    集群是一个3主3从的规模,3个master,每个master一个slave,这个集群中故障的Pod,在创建pvc后,进行过重启操作,导致现在的拓扑,有4个正常的master,一个无效的节点,原因是恢复的节点没有以slave的角色加入到集群,且集群没有forget掉之前故障的节点

    处理新节点

    从新的节点上看,没有无效的节点

    处理新节点比较简单,只需要对比下哪个master没有slave,将该节点设置为这个master的从节点即可:

    执行完命令之后,其他的节点上能看到该节点的角色变了

    监控中的拓扑也正常了,现在这种情况,集群是可以正常工作的,但是强迫症,必须要清除掉这个无效的节点。

    遗忘旧节点

    如果逐台执行cluster forget来遗忘这个无效的节点,由于集群之间会进行通信,同步拓扑信息,如果不是很快同事执行该操作,最后是无法保证成功的,所以写了个脚本,来模拟同时执行:

    bath-forget-nodes.sh

    #!/bin/bash
    
    set -e
    
    # 查出所有正常的节点(排除状态为fail的),需要在这些节点上执行forget操作 
    nodes_addrs=$(redis-cli -a $3 -h $1 -p $2 cluster nodes|grep -v fail| awk '{print $2}')
    echo " -------------normal cluster nodes -----------------"
    echo " $nodes_addrs "  
    echo " --------------------------------------------"  
    for addr in ${nodes_addrs[@]}; do
        host=${addr%:*}
        port=${addr#*:}
        # 查出所有需要forget的节点
        del_nodeids=$(redis-cli -a $3 -h $host -p $port cluster nodes|grep -E 'handshake|fail'| awk '{print $1}')
        for nodeid in ${del_nodeids[@]}; do
            echo " -------------delete nodes info -----------------------"  
            echo "delete from host: $host $port, delete node id: $nodeid "
            echo " ------------------------------------------------------"   
            # 执行forget            
            redis-cli -a $3 -h $host -p $port cluster forget $nodeid
        done
    done
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22

    一共是需要3个参数,IP、port、密码,最好先把执行forget的一行注释掉,看看输出是否符合预期。

    执行完之后,每个节点的拓扑都恢复正常了:

    大公告成,虽然是比较简单的操作,还是记录一下,好记性不如烂笔头。

  • 相关阅读:
    day09_数组进阶
    对vuex的理解,必须知道的知识点
    node.js: socket.io服务端和客户端交互示例
    TypeScript 泛型类型
    Vue组件之间的通信-父传子-子传父
    二元分类模型评估方法
    【H5写雷达图】使用h5写雷达图等动态图表(两种方式实现)
    Elasticsearch alias 使用
    2021 CCPC(Harbin)-B. Magical Subsequence
    多商户商城系统功能拆解27讲-平台端分销结算设置
  • 原文地址:https://blog.csdn.net/sinat_14840559/article/details/133272306