Aurora 蓝绿部署 Binlog 复制回滚指南
回滚方案对比
当蓝绿部署切换到绿环境后发现问题需要回滚时,有以下几种方案:
方案对比表
| 方案 | 回滚时间 | 数据丢失 | 复杂度 | 成本 |
|---|---|---|---|---|
| Binlog 复制 | 10分钟-2小时 | ✅ 无 | 低 | 无额外成本 |
| 快照恢复 | 30分钟-4小时 | ⚠️ 快照后的数据 | 低 | 快照存储费用 |
| DMS 同步 | 20分钟-3小时 | ✅ 无 | 中 | DMS 实例费用 |
| mysqldump 导出导入 | 数小时-数天 | ⚠️ 导出期间的数据 | 低 | 无 |
方案选择说明
本文档将聚焦Binlog 复制方案,考虑到以下原因:
- 速度最快(只同步增量数据,10分钟-2小时,取决于数据量)
- 零数据丢失(事务级精确同步)
- 零额外成本(使用 Aurora 原生功能)
- 可控性强(可随时查看进度、暂停、恢复)
其他方案适合场景:
- 快照恢复:binlog 已过期时的选择(会丢失快照后的数据)
- DMS 同步:需要数据转换或过滤时使用(有额外成本和配置复杂度)
- mysqldump:适合小数据库测试环境(< 10GB)
Binlog 复制原理
Binlog 复制是 MySQL 的标准主从复制功能,Aurora 通过存储过程封装了配置接口。
Binlog 复制过程:
1. 旧蓝环境作为"从库"
2. 从绿环境读取 binlog(从切换点开始)
3. 在旧蓝环境回放 binlog 中的变更
4. 追平后停止复制
5. 切换应用流量回旧蓝环境
前置条件说明
在执行回滚前,必须验证以下条件是否满足:
条件 1: Binlog 可用性验证(最关键)
验证方法:
-- 1. 连接到绿环境(当前生产环境),检查 binlog 保留设置
SELECT @@binlog_retention_hours;
-- 2. 查看可用的 binlog 文件列表
SHOW BINARY LOGS;
判断标准:
binlog 可用 = 切换时间 < (当前时间 - binlog 保留时长)
示例:
- Binlog 保留:72 小时
- 切换时间:2025-12-15 10:00
- 当前时间:2025-12-16 13:00
- 时间差:27 小时
- 结果:✅ 可用(27 < 72)
⚠️如果 binlog 不可用,请跳到"故障排查 - binlog 已过期"章节
条件 2: 复制用户验证
-- 连接到绿环境(当前生产环境)
SELECT user, host FROM mysql.user WHERE user = 'repl_user';
-- 如果不存在,创建复制用户:
CREATE USER 'repl_user'@'%' IDENTIFIED BY 'StrongPassword123!';
-- 注意:权限顺序应该是 REPLICATION CLIENT, REPLICATION SLAVE
GRANT REPLICATION CLIENT, REPLICATION SLAVE ON *.* TO 'repl_user'@'%';
FLUSH PRIVILEGES;
-- 验证权限
SHOW GRANTS FOR 'repl_user'@'%';
权限说明:
REPLICATION CLIENT:允许查询主库状态(SHOW MASTER STATUS)REPLICATION SLAVE:允许作为从库连接并读取 binlog
条件 3: 旧蓝环境可访问性验证
# 测试连接旧蓝环境
mysql -h old-blue-cluster.cluster-xxx.us-east-1.rds.amazonaws.com \
-u admin -p -e "SELECT VERSION();"
# 确认旧蓝环境没有写入
mysql -h old-blue-cluster... -e "SHOW PROCESSLIST;" | grep -i "insert\|update\|delete"
执行回滚步骤
步骤 1: 获取绿环境当前 binlog 位置
#!/bin/bash
# get-green-binlog-position.sh
GREEN_ENDPOINT="green-cluster.cluster-xxx.us-east-1.rds.amazonaws.com"
MYSQL_USER="admin"
MYSQL_PASS="your-password"
echo "=== 获取绿环境 binlog 位置 ==="
mysql -h $GREEN_ENDPOINT -u $MYSQL_USER -p$MYSQL_PASS -e "SHOW MASTER STATUS\G"
# 输出示例:
# File: mysql-bin-changelog.000123
# Position: 154
步骤 2: 在蓝环境配置复制
⚠️ 重要前置条件:必须启用 autocommit
-- 连接到蓝环境(原环境)
-- 1. 首先确认 autocommit 已启用(必须)
SHOW VARIABLES LIKE 'autocommit';
-- 如果显示 OFF,必须启用它
SET autocommit = 1;
-- 2. 根据 Aurora MySQL 版本选择对应的存储过程
-- ============================================
-- Aurora MySQL 3.x 版本(推荐)
-- ============================================
CALL mysql.rds_set_external_source(
'green-cluster.cluster-xxx.us-east-1.rds.amazonaws.com', -- 绿环境 endpoint
3306, -- 端口
'repl_user', -- 复制用户
'StrongPassword123!', -- 密码
'mysql-bin-changelog.000123', -- 切换时的 binlog 文件
154, -- 切换时的 binlog 位置
0 -- 0=不加密, 1=加密
);
-- ============================================
-- Aurora MySQL 2.x 版本
-- ============================================
CALL mysql.rds_set_external_master(
'green-cluster.cluster-xxx.us-east-1.rds.amazonaws.com',
3306,
'repl_user',
'StrongPassword123!',
'mysql-bin-changelog.000123',
154,
0
);
-- ============================================
-- 如果启用了 GTID(推荐)
-- ============================================
-- Aurora MySQL 3.x
CALL mysql.rds_set_external_source_with_auto_position(
'green-cluster.cluster-xxx.us-east-1.rds.amazonaws.com',
3306,
'repl_user',
'StrongPassword123!',
0
);
-- Aurora MySQL 2.x
CALL mysql.rds_set_external_master_with_auto_position(
'green-cluster.cluster-xxx.us-east-1.rds.amazonaws.com',
3306,
'repl_user',
'StrongPassword123!',
0
);
步骤 3: 启动复制
-- 启动复制
CALL mysql.rds_start_replication;
-- 立即检查状态
SHOW REPLICA STATUS\G
步骤 4: 监控复制进度
-- 持续监控(每 10 秒执行一次)
SHOW REPLICA STATUS\G
-- 关键指标:
-- Replica_IO_Running: Yes (必须是 Yes)
-- Replica_SQL_Running: Yes (必须是 Yes)
-- Seconds_Behind_Master: 0 (应该逐渐减少到 0)
-- Last_IO_Errno: 0 (必须是 0)
-- Last_SQL_Errno: 0 (必须是 0)
CloudWatch 监控(推荐):
Aurora 提供了 AuroraBinlogReplicaLag 指标来监控 binlog 复制延迟:
# 1. 查看 AuroraBinlogReplicaLag 指标
aws cloudwatch get-metric-statistics \
--namespace AWS/RDS \
--metric-name AuroraBinlogReplicaLag \
--dimensions Name=DBInstanceIdentifier,Value=old-blue-instance-1 \
--start-time $(date -u -d '1 hour ago' +%Y-%m-%dT%H:%M:%S) \
--end-time $(date -u +%Y-%m-%dT%H:%M:%S) \
--period 60 \
--statistics Average
# 2. 创建告警(当复制延迟超过 60 秒时告警)
aws cloudwatch put-metric-alarm \
--alarm-name aurora-binlog-replication-lag \
--alarm-description "Alert when binlog replication lag > 60 seconds" \
--metric-name AuroraBinlogReplicaLag \
--namespace AWS/RDS \
--statistic Average \
--period 60 \
--evaluation-periods 2 \
--threshold 60 \
--comparison-operator GreaterThanThreshold \
--dimensions Name=DBInstanceIdentifier,Value=old-blue-instance-1
关键 CloudWatch 指标说明:
| 指标名称 | 说明 | 单位 |
|---|---|---|
AuroraBinlogReplicaLag |
Binlog 复制延迟(包括外部复制) | 毫秒 |
AuroraReplicaLag |
Aurora Replica 之间的复制延迟 | 毫秒 |
DatabaseConnections |
当前数据库连接数 | 计数 |
CPUUtilization |
CPU 使用率 | 百分比 |
监控脚本参考:
#!/bin/bash
# monitor-replication.sh - 监控复制进度
BLUE_ENDPOINT="old-blue-cluster.cluster-xxx.us-east-1.rds.amazonaws.com"
MYSQL_USER="admin"
MYSQL_PASS="your-password"
echo "=== 开始监控复制进度 ==="
while true; do
clear
echo "监控时间: $(date)"
echo "================================"
mysql -h $BLUE_ENDPOINT -u $MYSQL_USER -p$MYSQL_PASS -e "SHOW REPLICA STATUS\G" | \
grep -E "Replica_IO_Running|Replica_SQL_Running|Seconds_Behind_Master|Last_IO_Errno|Last_SQL_Errno"
# 检查是否已追平
SECONDS_BEHIND=$(mysql -h $BLUE_ENDPOINT -u $MYSQL_USER -p$MYSQL_PASS -sN -e "
SHOW REPLICA STATUS\G" | grep "Seconds_Behind_Master:" | awk '{print $2}')
if [ "$SECONDS_BEHIND" == "0" ]; then
echo ""
echo "✅ 复制已追平!可以停止复制。"
break
fi
echo ""
echo "当前延迟: $SECONDS_BEHIND 秒"
sleep 10
done
步骤 5: 停止复制并清理
-- 确认已追平后,停止复制
CALL mysql.rds_stop_replication;
-- 再次检查状态
SHOW REPLICA STATUS\G
-- 清理复制配置
-- Aurora MySQL 3.x
CALL mysql.rds_reset_external_source;
-- Aurora MySQL 2.x
CALL mysql.rds_reset_external_master;
-- 验证清理成功
SHOW REPLICA STATUS\G
-- 应该返回空结果或显示 "Empty set"
步骤 6: 切换流量回蓝环境
#!/bin/bash
# switch-back-to-blue.sh
# 1. 停止应用写入绿环境
echo "⚠️ 请确保应用已停止写入绿环境"
read -p "按 Enter 继续..."
# 2. 更新应用配置指向蓝环境
echo "更新应用数据库连接字符串..."
# 根据你的部署方式更新(如更新 SSM 参数、环境变量等)
# 3. 重启应用或刷新配置
echo "重启应用服务..."
# kubectl rollout restart deployment/your-app
# 或其他重启命令
# 4. 验证连接
echo "验证应用连接到蓝环境..."
时间估算
| 阶段 | 时间 | 说明 |
|---|---|---|
| 准备配置 | 5 分钟 | 获取 binlog 位置、配置复制 |
| 启动复制 | 1 分钟 | 执行存储过程 |
| 数据同步 | 10 分钟 - 2 小时 | 取决于数据量和写入速率 |
| 停止清理 | 2 分钟 | 停止复制、清理配置 |
| 应用切换 | 5-10 分钟 | 更新配置、重启服务 |
| 总计 | 20 分钟 - 2.5 小时 | 大部分时间在等待数据同步 |
故障排查
问题 1: 复制无法启动
-- 检查错误信息
SHOW REPLICA STATUS\G
-- 常见错误:
-- Last_IO_Errno: 1236 - binlog 位置不存在
-- 解决方案:使用下一个 binlog 文件
CALL mysql.rds_next_source_log(123); -- 123 是当前 binlog 索引
CALL mysql.rds_start_replication;
-- Last_IO_Errno: 1045 - 认证失败
-- 解决方案:检查复制用户密码和权限
问题 2: 复制延迟过大
-- 检查绿环境负载
SHOW PROCESSLIST;
-- 检查蓝环境性能
SHOW ENGINE INNODB STATUS\G
-- 临时增加并行复制线程(Aurora MySQL 3.x)
SET GLOBAL replica_parallel_workers = 4;
问题 3: binlog 已过期
# 如果 binlog 已被清理,只能使用快照恢复
# 1. 停止绿环境写入
# 2. 创建绿环境快照
aws rds create-db-cluster-snapshot \
--db-cluster-identifier green-cluster \
--db-cluster-snapshot-identifier green-rollback-snapshot
# 3. 从快照恢复到蓝环境(需要较长时间)