一、高可用是什么意思?
高可用(High Availability, HA)的核心是消除单点故障(Single Point of Failure, SPOF)。即系统中任何一个组件坏了,整个系统都不会挂,用户几乎无感知。
通常用"几个9"来衡量可用性:
-
99.9%(三九):一年约8.77小时不可用。
-
99.99%(四九):一年约52.6分钟不可用。
-
99.999%(五九):一年约5.26分钟不可用。
注意:100%的可用性在现实中不存在,因为计划内维护(如升级、打补丁)也需要时间。
二、核心实现方式
高可用主要通过冗余 和自动故障转移来实现。
1. 主备模式
-
描述:一台主节点工作,一台或多台备用节点热待命,实时同步数据。主节点故障时,备节点自动接管。
-
优点:实现简单,数据一致性好。
-
缺点:存在资源浪费(备机平时不用),切换有短暂中断。
-
典型场景:数据库(MySQL主从+自动切换)、Keepalived + VIP。
2. 主主模式
-
描述:两台节点同时工作,互为备份,共同分担流量。任意一台故障,另一台承担全部工作。
-
优点:资源利用率高,切换快。
-
缺点:数据冲突风险高(如两台同时写同一行数据),实现复杂。
-
典型场景:某些DNS系统、轻量级数据库集群(如MariaDB Galera)。
3. 集群模式
-
描述:多台节点组成集群,前端用负载均衡器分发请求。故障节点被自动摘除,业务不受影响。
-
优点:真正的高扩展和高可用,节点故障几乎无感知。
-
缺点:架构复杂,需要负载均衡器和共享存储或分布式存储。
-
典型场景:Web服务器集群(Nginx + 多个Tomcat)、Kubernetes容器集群。
4. 数据层高可用
-
同步复制 :数据必须同时写入主库和备库才返回成功。强一致性,但性能影响大。
-
异步复制 :主库写入后立即返回,后台同步到备库。性能好,但可能丢失少量数据。
-
半同步复制:至少一个备库写入成功才返回。平衡了性能和数据安全。
三、需要具备哪些实现条件?
要实现真正的高可用,必须满足以下技术条件:
| 条件 | 说明 | 关键技术 |
|---|---|---|
| 1. 冗余无单点 | 所有可能故障的组件(服务器、网络、电源)都至少有两份。 | 双网卡绑定、双电源、多机多活、RAID磁盘阵列 |
| 2. 故障自动检测 | 能快速、准确判断节点是"真故障"还是"网络抖动",避免误切换。 | 心跳检测、健康检查(Ping/端口/接口)、Quorum仲裁机制 |
| 3. 自动切换(Failover) | 检测到故障后,系统自动将VIP或流量切换到备用节点,无需人工介入。 | VIP漂移(如Keepalived)、DNS切换(需短TTL)、负载均衡摘除节点 |
| 4. 数据一致性保障 | 切换后,新主节点的数据必须完整且最新,不能出现"脑裂"(两个主节点同时写数据)。 | 共享存储(SAN/NAS)、分布式一致性协议(Raft/Paxos)、 fencing(隔离故障节点) |
| 5. 快速恢复能力 | 故障节点修复后能快速重新加入集群,自动同步缺失的数据。 | 增量数据同步、全量数据重建机制 |
四、一个典型的高可用架构示例
常见的LVS + Keepalived + Nginx + MySQL主从架构:
-
接入层:用VRRP协议实现VIP在两台LVS/Keepalived之间漂移。主LVS故障,备LVS接管VIP,用户无感。
-
应用层:多个Nginx节点组成集群,前端负载均衡器分发请求。某个Nginx宕机,流量自动切到其他节点。
-
数据层:MySQL采用主从复制 + 自动切换工具(如MHA/Orchestrator)。主库故障,从库自动升级为新主库,应用只需修改数据源连接。
总结: 高可用就是用一堆普通机器 和一套自动容灾机制 ,模拟出一台永不掉线的超级机器的效果。代价是成本增加和架构复杂度提升。
高可用需要多台服务器 ,其中服务层多实例部署 ,而数据库/缓存层采用主从复制或集群,这两层通常跑在不同服务器上,避免资源冲突
五、核心原则:消除单点,而非简单克隆
高可用要求任何一个组件(服务器、进程、磁盘、网络)失效时,仍有其他冗余组件能接管工作。但这并不意味着每台服务器上都要把"所有服务+所有数据库"都部署一份。这样做反而会带来资源冲突、数据竞争、维护复杂等问题。
六、常见的合理冗余模式(不是"每台都部署所有")
1. 服务层(无状态)
-
做法 :在两台或更多服务器上部署相同的服务实例(比如你的 Ocelot、Nginx)。
-
特点:每台服务器只跑服务,不跑数据库。前端用负载均衡分发请求。
-
结论 :✅ 这是"多套服务",但服务器上不部署数据库。
2. 数据库层(有状态)
-
做法 :通常是主从复制 或集群。
-
主库(Active)负责读写,部署在服务器A。
-
从库(Standby/Read-only)同步数据,部署在服务器B(或更多)。
-
主库故障时,将从库提升为新主库。
-
-
特点 :并不是两台服务器都同时提供写服务(双主模式除外,但双主风险高)。从库平时可能只读,或者完全不接受流量。
-
结论 :❌ 不是"两套数据库都同时对外提供完整服务",而是一套主用,一套热备/只读。
3. Redis 缓存
-
做法:
-
哨兵模式:一主一从或一主多从,主负责写,从负责读或仅备份。故障时哨兵自动切换。
-
集群模式:多个分片,每个分片有主从。
-
-
结论 :❌ 也不是"两套完全独立的 Redis 同时读写",而是主从结构。
七、为什么"主备服务器都部署全套服务+数据库"不好?
假设你有两台物理机,每台都运行:Nginx + Ocelot + MySQL + Redis。
| 问题 | 说明 |
|---|---|
| 端口冲突 | 两台机器各自运行 MySQL 占用 3306 端口没问题(不同IP),但你的应用程序要连接哪个 MySQL?如果都连本机的,数据就不一致。 |
| 数据不一致 | 两个 MySQL 独立运行,没有复制关系,写入 A 机的数据 B 机看不到,切换后数据丢失。 |
| 资源浪费 | 数据库和缓存非常消耗内存、CPU、磁盘 I/O。每台都跑全量数据库,硬件成本翻倍,且备用机平时几乎闲置。 |
| 维护复杂 | 升级、备份、监控都要做两份,且要处理两套数据之间的同步问题,比标准的主从复制复杂得多。 |
八、正确的高可用资源规划示例(架构如下)
| 层级 | 组件 | 采用的高可用模式 |
|---|---|---|
| 入口负载均衡 | Nginx + Pacemaker | 主备模式(Active-Standby) |
| 内部网关服务 | Ocelot 集群 + Consul | 集群模式(多活 + 服务发现) |
| 配置中心 | Consul 集群 | 分布式集群模式(Raft) |
| 数据库 | MySQL(需自行配置) | 通常为主备/主主或集群 |
| 缓存 | Redis(需自行配置) | 通常为哨兵(主备)或集群 |
假设你有 4 台物理机/虚拟机:
| 服务器 | 部署内容 | 角色 |
|---|---|---|
| 主机 A | Nginx (Pacemaker 主) + Ocelot 实例1 | 入口主节点,网关实例 |
| 主机 B | Nginx (Pacemaker 备) + Ocelot 实例2 | 入口备节点,网关实例 |
| 主机 C | MySQL 主库 + Redis 主节点 | 数据主节点 |
| 主机 D | MySQL 从库 + Redis 从节点 | 数据备节点 |
-
服务层:Ocelot 在 A、B 上都运行,Nginx 通过 Consul 发现所有 Ocelot 实例,流量分发到 A 和 B。一台 Ocelot 挂了,Nginx 切到另一台。
-
数据层:MySQL 主从复制,Redis 主从复制。C 故障时,D 接管成为新主。
-
入口层:VIP 绑定在 A 的 Nginx,A 故障时 VIP 漂移到 B。
这样一共 4 台服务器,没有一台运行"所有组件",但实现了高可用。