Skip to content

14|高可用:InnoDB Cluster

上一篇搭了主从复制。但主从是手工切换——主库挂了,要人半夜爬起来把从库提成主库、改应用连接。这个过程几分钟到几十分钟,期间服务不可用。

高可用解决的就是这个——主库挂了,自动切换、应用自动连到新主、服务尽快恢复。本篇讲 MySQL 官方的高可用方案 InnoDB Cluster,以及它底层的手工切换逻辑。

先分清三个概念:

能力解决什么
备份误删后回退到过去某时间点
复制数据实时传到多个实例
高可用故障后服务自动恢复

高可用解决服务可用性,不能修复误删的数据——那要靠备份和 binlog。

一、主从手工切换:理解切换在做什么

自动切换底层就是手工切换。先理解手工切的过程:

text
1. 确认主库不可用
2. 选延迟最小、数据最全的从库
3. 停该从库复制(不再接收旧主变更)
4. 关闭只读,宣布它为新主
5. 改应用连接入口(指向新主)
6. 其他从库改挂新主
7. 旧主恢复后以从库身份加入

核心 SQL:

sql
-- 新主:停止复制、关只读
STOP REPLICA;
RESET REPLICA ALL;
SET GLOBAL super_read_only = OFF;

-- 其他从库:改指向新主
CHANGE REPLICATION SOURCE TO
  SOURCE_HOST='10.0.0.20', SOURCE_PORT=3306,
  SOURCE_USER='repl', SOURCE_PASSWORD='...',
  SOURCE_AUTO_POSITION=1;
START REPLICA;

第 5 步改应用连接是难点——应用配的是旧主地址,切到新主要改配置、重启或靠 VIP/DNS。这个衔接不好,切换就是"数据库切了但应用还在连旧主",服务还是不可用。高可用方案要解决的就是让这个衔接自动化。

二、InnoDB Cluster 是什么

InnoDB Cluster 是 MySQL 官方的高可用方案,三个组件:

组件作用
Group Replication多个 MySQL 组成集群,自动复制、自动故障检测
MySQL Router连接入口,自动把读写路由到正确的节点
MySQL Shell管理工具,建集群、加节点、查状态
text
应用 → MySQL Router → 主(读写)+ 从(只读)

                     Group Replication 自动同步

应用连的是 Router,不是直接连 MySQL。Router 知道哪个是主、哪个是从,自动路由——写请求到主、读请求到从。主挂了,Group Replication 自动选新主,Router 自动把流量切过去,应用不用改连接配置。

这就是它比手工主从强的地方——切换和应用衔接都自动化了。

三、Group Replication 的特点

Group Replication(MGR)是 InnoDB Cluster 的底层,多个 MySQL 组成一个组,互相复制:

  • 自动故障检测:主挂了,组里其他节点投票检测,自动选新主
  • 多数派:集群要过半节点存活才能服务(3 节点挂 1 个还能用,挂 2 个不行)
  • 强一致:事务要多数节点确认才算提交(比异步复制更安全,但延迟略高)

集群节点数推荐奇数(3、5、7)——便于投票多数派。3 节点是最小可用配置,挂 1 个还能服务。

四、搭建 InnoDB Cluster(概念流程)

具体命令细节看官方文档,这里讲流程和理解:

text
1. 准备 3 台 MySQL,配好 binlog 和 GTID(和主从复制一样)
2. 每台装 Group Replication 插件
3. 用 MySQL Shell 建集群:
   dba.createCluster('myCluster')
   cluster.addInstance('10.0.0.2')
   cluster.addInstance('10.0.0.3')
4. 部署 MySQL Router,指向集群
5. 应用连 Router

dba.createCluster 是 MySQL Shell 提供的命令,封装了 Group Replication 的配置。加节点用 cluster.addInstance——新节点用 Clone 插件从主库同步数据(上一篇讲的 Clone 在这里自动用上),不用手动初始化。

Router 可以部署多份(和应用一起),避免 Router 自己成单点。

五、故障切换怎么发生

主库挂了,集群自动处理:

text
1. 其他节点发现主不响应(心跳超时)
2. 多数节点确认主挂了,触发重新选举
3. 选一个数据最新的从当新主
4. Router 感知到拓扑变化,把写流量路由到新主
5. 应用无感知(连的还是 Router,Router 内部切了)

整个过程通常几秒到几十秒。期间写请求会失败重试,读请求如果 Router 配了允许走从库则不受影响。

RTO(恢复时间)和 RPO(数据丢失):

  • RTO:故障到恢复的时间,InnoDB Cluster 几秒到几十秒
  • RPO:可能丢失多少数据,强一致模式下基本不丢(多数确认才算提交)

六、读写分离

Router 可以配读写分离——写走主、读走从:

text
读写端口(6446)→ 主
只读端口(6447)→ 从

应用按需求连不同端口。一致性要求高的查询(刚写入就要查到)走读写端口(主),报表、统计这类走只读端口(从)。

注意从库有延迟——刚写入的数据从库可能还没回放,走只读端口查不到。对延迟敏感的走主。

七、InnoDB Cluster 的取舍

不是所有场景都该上 InnoDB Cluster:

场景适不适合
单库、能接受分钟级停机手工主从够了,别上集群
需要高可用、有专人维护InnoDB Cluster
超大规模、跨机房InnoDB Cluster + ClusterSet 或云托管
老环境已有 MHA可继续用,新环境别再用 MHA(MHA 已老旧)

InnoDB Cluster 运维复杂度比单机主从高——3 个节点要维护、Router 要部署、集群状态要监控。小项目或能接受短停机的,手工主从更简单。核心业务、不能停的,才值得上集群。

八、故障演练

上线后要定期演练——模拟主库挂了,看集群切不切得动:

bash
# 在主库上模拟故障
systemctl stop mysqld

观察:集群是否检测到、是否选了新主、Router 是否把流量切过去、应用是否自动恢复。演练能发现配置问题(比如 Router 没感知到、应用连接超时太短),别等真故障才发现。

高可用之后

数据存好(安装/SQL/索引)、性能调好(InnoDB/调优)、安全管好(账号)、备份做好、复制和高可用搭好。最后讲常见故障排查——把这些综合起来,出问题时怎么定位。