RocketMQ 故障演练是保障集群稳定运行的关键。本文将深入探讨各种故障场景的演练方法和应急预案。
一、故障演练基础
1.1 演练目标
演练目标:
1. 验证集群高可用能力
2. 测试故障恢复时间
3. 验证监控告警有效性
4. 提升团队应急能力
5. 完善应急预案
1.2 演练原则
演练原则:
1. 在测试环境先演练
2. 选择低峰期执行
3. 准备回滚方案
4. 全程监控记录
5. 演练后总结改进
1.3 演练分类
| 分类 | 说明 | 频率 |
|---|---|---|
| Broker 故障 | Broker 宕机、重启 | 每月 |
| NameServer 故障 | NameServer 宕机、切换 | 每月 |
| 网络故障 | 网络分区、延迟 | 每季度 |
| 磁盘故障 | 磁盘满、IO 慢 | 每季度 |
| 全链路故障 | 多组件同时故障 | 每半年 |
二、Broker 故障演练
2.1 Master 宕机
演练步骤:
#!/bin/bash
# Master 宕机演练脚本
echo "=== Master 宕机演练 ==="
# 1. 记录演练开始时间
START_TIME=$(date +%s)
echo "演练开始时间:$(date)"
# 2. 记录当前状态
echo -e "\n=== 演练前状态 ==="
mqadmin clusterList -n ns1:9876 > /tmp/cluster_before.txt
mqadmin consumerProgress -n ns1:9876 > /tmp/consumers_before.txt
# 3. 停止 Master Broker
echo -e "\n=== 停止 Master Broker ==="
ssh broker-a "systemctl stop rocketmq-broker"
# 4. 监控集群状态
echo -e "\n=== 监控集群状态 ==="
for i in {1..10}; do
echo "检查 $i/10..."
# 检查 Broker 状态
mqadmin clusterList -n ns1:9876 2>/dev/null | grep broker-a
echo "Slave 是否接管:$(ssh broker-b 'systemctl is-active rocketmq-broker')"
# 检查 Consumer Lag
lag=$(mqadmin consumerProgress -n ns1:9876 2>/dev/null | awk 'NR>3 {sum+=$5} END {print sum}')
echo "消费堆积:$lag"
sleep 10
done
# 5. 启动 Master Broker
echo -e "\n=== 启动 Master Broker ==="
ssh broker-a "systemctl start rocketmq-broker"
# 6. 等待恢复
echo -e "\n=== 等待恢复 ==="
sleep 60
# 7. 验证恢复
echo -e "\n=== 验证恢复 ==="
mqadmin clusterList -n ns1:9876 > /tmp/cluster_after.txt
mqadmin consumerProgress -n ns1:9876 > /tmp/consumers_after.txt
# 8. 计算恢复时间
END_TIME=$(date +%s)
DURATION=$((END_TIME - START_TIME))
echo -e "\n演练结束时间:$(date)"
echo "演练持续时间:$DURATION 秒"
2.2 Slave 宕机
演练步骤:
#!/bin/bash
# Slave 宕机演练脚本
echo "=== Slave 宕机演练 ==="
# 1. 停止 Slave Broker
echo "停止 Slave Broker..."
ssh broker-b "systemctl stop rocketmq-broker"
# 2. 验证 Master 仍可用
echo "验证 Master 可用性..."
echo "test" | mqadmin sendMessage -n ns1:9876 -b broker-a:10911 -t test-topic
# 3. 启动 Slave Broker
echo "启动 Slave Broker..."
ssh broker-b "systemctl start rocketmq-broker"
# 4. 等待同步
sleep 60
# 5. 验证恢复
mqadmin clusterList -n ns1:9876
三、NameServer 故障演练
3.1 单 NameServer 宕机
演练步骤:
#!/bin/bash
# NameServer 宕机演练脚本
echo "=== NameServer 宕机演练 ==="
# 1. 停止 NameServer
echo "停止 NameServer..."
ssh ns1 "systemctl stop rocketmq-namesrv"
# 2. 验证 Producer/Consumer 仍可用
echo "验证 Producer/Consumer 可用性..."
echo "test" | mqadmin sendMessage -n ns2:9876 -t test-topic
# 3. 启动 NameServer
echo "启动 NameServer..."
ssh ns1 "systemctl start rocketmq-namesrv"
# 4. 等待恢复
sleep 30
# 5. 验证恢复
mqadmin namesrvStatus -n ns2:9876
3.2 多 NameServer 宕机
演练步骤:
#!/bin/bash
# 多 NameServer 宕机演练脚本
echo "=== 多 NameServer 宕机演练 ==="
# 1. 停止所有 NameServer
echo "停止所有 NameServer..."
ssh ns1 "systemctl stop rocketmq-namesrv"
ssh ns2 "systemctl stop rocketmq-namesrv"
# 2. 验证 Producer/Consumer 不可用
echo "验证 Producer/Consumer 不可用..."
mqadmin clusterList -n ns1:9876 2>&1 | head -3
# 3. 启动 NameServer
echo "启动 NameServer..."
ssh ns1 "systemctl start rocketmq-namesrv"
ssh ns2 "systemctl start rocketmq-namesrv"
# 4. 等待恢复
sleep 60
# 5. 验证恢复
mqadmin clusterList -n ns1:9876
四、网络故障演练
4.1 网络分区
演练步骤:
#!/bin/bash
# 网络分区演练脚本
echo "=== 网络分区演练 ==="
# 1. 模拟网络分区(使用 iptables)
echo "创建网络分区..."
ssh broker-a "iptables -A OUTPUT -d broker-b -j DROP"
ssh broker-a "iptables -A OUTPUT -d ns2 -j DROP"
# 2. 验证分区效果
echo "验证分区..."
ssh broker-a "ping -c 1 broker-b"
# 3. 监控集群状态
echo "监控集群状态..."
for i in {1..10}; do
echo "检查 $i/10..."
mqadmin clusterList -n ns1:9876 2>&1 | head -5
sleep 10
done
# 4. 恢复网络
echo "恢复网络..."
ssh broker-a "iptables -F"
# 5. 验证恢复
sleep 60
mqadmin clusterList -n ns1:9876
4.2 网络延迟
演练步骤:
#!/bin/bash
# 网络延迟演练脚本
echo "=== 网络延迟演练 ==="
# 1. 添加网络延迟
echo "添加 100ms 延迟..."
ssh broker-a "tc qdisc add dev eth0 root netem delay 100ms"
# 2. 验证延迟
echo "验证延迟..."
ssh broker-a "ping -c 3 broker-b"
# 3. 监控性能
echo "监控性能..."
for i in {1..10}; do
echo "检查 $i/10..."
# 检查 Producer 延迟
mqadmin sendMessage -n ns1:9876 -t test-topic -m "test" 2>&1 | grep -i "cost"
sleep 10
done
# 4. 移除延迟
echo "移除延迟..."
ssh broker-a "tc qdisc del dev eth0 root netem delay 100ms"
# 5. 验证恢复
sleep 30
mqadmin clusterList -n ns1:9876
五、磁盘故障演练
5.1 磁盘满
演练步骤:
#!/bin/bash
# 磁盘满演练脚本
echo "=== 磁盘满演练 ==="
# 1. 检查当前磁盘使用
echo "当前磁盘使用:"
ssh broker-a "df -h /data/rocketmq/store"
# 2. 创建大文件填满磁盘
echo "创建大文件..."
ssh broker-a "dd if=/dev/zero of=/data/rocketmq/store/fillfile bs=1G count=10"
# 3. 监控告警
echo "监控告警..."
# 检查是否触发磁盘告警
# 4. 清理文件
echo "清理文件..."
ssh broker-a "rm /data/rocketmq/store/fillfile"
# 5. 验证恢复
ssh broker-a "df -h /data/rocketmq/store"
5.2 磁盘 IO 慢
演练步骤:
#!/bin/bash
# 磁盘 IO 慢演练脚本
echo "=== 磁盘 IO 慢演练 ==="
# 1. 限制磁盘 IO
echo "限制磁盘 IO..."
ssh broker-a "ionice -c3 -p \$(pgrep -f rocketmq-broker)"
# 2. 监控性能
echo "监控性能..."
for i in {1..10}; do
echo "检查 $i/10..."
ssh broker-a "iostat -x 1 1 | grep -A1 Device"
sleep 10
done
# 3. 恢复 IO
echo "恢复 IO..."
ssh broker-a "ionice -c2 -p \$(pgrep -f rocketmq-broker)"
# 4. 验证恢复
sleep 30
ssh broker-a "iostat -x 1 1 | grep -A1 Device"
六、应急预案
6.1 预案模板
# RocketMQ 故障应急预案
## 故障信息
- 故障时间:YYYY-MM-DD HH:MM:SS
- 故障类型:Broker 宕机/NameServer 故障/网络故障/磁盘故障
- 影响范围:Topic/Consumer Group
## 应急步骤
### 1. 故障确认
- [ ] 确认故障现象
- [ ] 确认影响范围
- [ ] 通知相关人员
### 2. 故障处理
- [ ] 执行故障切换
- [ ] 重启故障组件
- [ ] 验证集群状态
### 3. 恢复验证
- [ ] 验证 Producer 正常
- [ ] 验证 Consumer 正常
- [ ] 验证监控指标
### 4. 事后总结
- [ ] 记录故障原因
- [ ] 记录处理过程
- [ ] 提出改进建议
6.2 应急联系人
# emergency-contacts.yml
emergency_contacts:
- name: 运维负责人
phone: 138-xxxx-xxxx
role: 应急指挥
- name: RocketMQ 专家
phone: 139-xxxx-xxxx
role: 技术支持
- name: 网络工程师
phone: 137-xxxx-xxxx
role: 网络支持
- name: DBA
phone: 136-xxxx-xxxx
role: 数据库支持
6.3 应急工具包
#!/bin/bash
# 应急工具包
# 1. 集群状态检查
check_cluster_status() {
mqadmin clusterList -n ns1:9876
mqadmin consumerProgress -n ns1:9876
mqadmin namesrvStatus -n ns1:9876
}
# 2. Broker 重启
restart_broker() {
local broker=$1
ssh $broker "systemctl restart rocketmq-broker"
}
# 3. 消费者重置
reset_consumer_offset() {
mqadmin resetOffsetByTime -n ns1:9876 \
-t $1 -g $2 -s $(date +%s)000 -f true
}
# 4. 日志收集
collect_logs() {
local broker=$1
ssh $broker "tail -1000 /var/log/rocketmq/broker.log" > logs/$broker.log
}
七、演练总结
7.1 演练报告模板
# 故障演练报告
## 演练信息
- 演练时间:YYYY-MM-DD HH:MM:SS
- 演练类型:Broker 宕机/NameServer 故障/网络故障/磁盘故障
- 参与人员:xxx、xxx、xxx
## 演练过程
### 1. 演练前状态
- NameServer 数量:2
- Broker 数量:2
- Topic 数量:10
- Consumer Group 数量:5
### 2. 演练步骤
1. HH:MM:SS - 开始演练
2. HH:MM:SS - 执行故障注入
3. HH:MM:SS - 观察集群状态
4. HH:MM:SS - 执行恢复操作
5. HH:MM:SS - 验证恢复
6. HH:MM:SS - 演练结束
### 3. 演练结果
- 故障检测时间:30 秒
- 故障恢复时间:120 秒
- 数据丢失:无
- 服务中断:是(60 秒)
## 问题分析
1. 问题 1:...
原因:...
改进:...
2. 问题 2:...
原因:...
改进:...
## 改进建议
1. 优化监控告警
2. 完善应急预案
3. 增加自动恢复
4. 定期演练
7.2 改进跟踪
# 改进跟踪表
| 改进项 | 负责人 | 状态 | 完成时间 |
|--------|--------|------|----------|
| 优化监控告警 | 张三 | 进行中 | 2026-09-30 |
| 完善应急预案 | 李四 | 已完成 | 2026-09-15 |
| 增加自动恢复 | 王五 | 计划中 | 2026-10-30 |
| 定期演练 | 赵六 | 进行中 | 持续 |
总结
RocketMQ 故障演练的核心要点:
- 故障场景:Broker 宕机、NameServer 故障、网络分区、磁盘故障
- 演练方法:脚本自动化、监控记录
- 应急预案:预案模板、联系人、工具包
- 演练总结:报告模板、改进跟踪
核心要点:
- 定期执行故障演练
- 建立完善的应急预案
- 记录演练过程和问题
- 持续改进优化
- 提升团队应急能力
参考资料
- RocketMQ 运维官方文档
- Chaos Engineering
- 《SRE:Google 运维解密》