主备容灾:两台 VPS 做故障自动切换,小业务也用得起
单台 VPS 挂了业务就停?小够讲小业务的主备容灾:RTO/RPO 通俗解读、数据同步、DNS 切换、演练流程,两台便宜 VPS 就能搭起故障切换,不用买贵方案。
我是小够。备份是"数据丢了能找回来",容灾是"机器挂了业务不停"。备份人人都在做,容灾很多人觉得那是大厂的事——其实小业务也能做,两台便宜 VPS 就够。这篇把主备容灾讲透,不堆概念,只讲能落地的。
先搞懂两个词:RTO 和 RPO
容灾圈有两个黑话,翻译成人话:
- RTO(恢复时间目标):挂了之后,多久能恢复?1 小时还是 1 天?
- RPO(恢复点目标):最多能丢多少数据?1 小时的数据还是 1 天的?
小够的建议:先给自己的业务定个数。比如个人博客:RTO 4 小时、RPO 24 小时,完全可以接受。小电商:RTO 1 小时、RPO 1 小时。有了目标,方案才知道做到什么程度——容灾做到"够用"就行,别为用不上的指标花钱。
架构:主备两台
[DNS]
/ \
[主VPS] [备VPS]
跑业务 待命+同步数据
- 主:正常跑业务
- 备:平时待命,数据实时/定时从主同步过来
- 故障时:把流量切到备机
备机平时可以跑点不重要的东西(监控、测试),别让它完全闲置,闲置的机器出故障了你都不知道。
数据同步:核心中的核心
切换的前提是备机的数据是新的。分两层:
文件同步:rsync 定时同步,前面讲过:
# 在备机上定时从主机拉
rsync -az --delete user@primary:/var/www/ /var/www/
数据库同步:主从复制。MySQL/PostgreSQL 都支持,备库实时跟着主库走。配一次,之后自动同步。注意:主从有延迟(通常秒级),RPO 就取决于这个延迟。
不同步什么:日志、缓存、临时文件不同步,只同步"丢了会心疼的"。
切换:DNS 是最通用的方案
VPS 容灾切换最常用的办法是 DNS 切换:
- 平时域名 A 记录指向主机 IP
- 主机挂了,把 A 记录改成备机 IP
- 等 DNS 生效,流量就过去了
关键点:TTL 提前调小。平时 TTL 设 300 秒(5 分钟),故障时改记录,全球大部分地区几分钟内生效。如果 TTL 是 24 小时,切换了也要等一天,黄花菜都凉了。
# 平时就把 TTL 设小,应急时才来得及
# 以 Cloudflare 等 DNS 服务商为例,TTL 300
小够提醒:keepalived + 浮动 IP 是更高级的方案(秒级切换),但多数 VPS 商家不支持浮动 IP,别照着教程硬套。DNS 切换虽然慢几分钟,但通用、便宜、够用。
切换 checklist:故障时别慌
提前写好,贴在备忘录里,故障时照着打勾:
- 确认主机真的挂了(不是自己网络问题:换个网络 ping 一下)
- 确认备机数据是最新的(看最后一次同步时间)
- 备机上启动业务服务(平时待命的服务先起起来)
- DNS A 记录切到备机 IP
- 用手机流量访问一次,确认业务正常
- 发公告(如果有用户的话)
- 修主机,修好后数据反向同步,再决定切不切回去
第 1 条最重要:别把"我家断网了"当成"服务器挂了",先确认。
演练:不演练等于没有
容灾方案最大的坑是"从来没试过"。每季度演练一次:
- 挑个业务低峰期(比如周日凌晨)
- 按 checklist 走一遍完整切换
- 计时:RTO 达标了吗?数据丢了多少?RPO 达标了吗?
- 记录问题,修方案
演练一定会发现问题——这就是演练的意义。真故障时第一次用这套流程,基本都会翻车。
成本
两台 VPS,一台主力、一台备机(备机可以配置低一点,只保证能跑起来)。对比业务中断几小时的损失,这钱花得值。但小够也要说句实在话:个人博客、小实验项目,真没必要做主备——做好备份就行,RTO 4 小时完全可以接受。容灾是给"停不起"的业务准备的,别为用不上的指标花钱。
什么时候不做主备
- 纯个人博客/实验项目:备份做好就行
- 业务能容忍半天中断:修机器比养备机便宜
- 数据不重要:丢了重搭的,随缘
什么时候必须做
- 靠网站吃饭:电商、接单、SaaS,停一小时就丢钱
- 有用户在用:服务挂了影响别人
- 合规要求:某些业务要求有容灾方案
常见问题
Q:备机平时完全闲置吗? A:别完全闲置。跑点监控、测试环境之类的轻量东西,既利用了资源,又能保证机器是活的。完全闲置的机器,故障时才发现它三个月前就起不来了。
Q:DNS 切换期间,部分用户还在访问旧 IP 怎么办? A:正常。DNS 全球生效需要时间,TTL 300 秒的情况下,大部分地区几分钟内完成。极少数地区的旧缓存可能撑几小时,接受这个现实。
Q:主备切换后,数据写到备机了,主机修好怎么合并? A:这是最难的部分。简单方案:修好后把备机当成新的主,旧主机降级成备(反向同步一次)。双向同步容易冲突,别碰。
Q:演练会影响线上业务吗? A:选低峰期,提前公告。演练本身就是一次"可控的故障",比真故障时手忙脚乱强一百倍。
MySQL 主从复制实战
数据库同步用主从复制,备库实时跟着主库:
# 主库 my.cnf
server-id = 1
log_bin = mysql-bin
binlog_format = ROW
# 主库建复制用户
CREATE USER 'repl'@'%' IDENTIFIED BY '强密码';
GRANT REPLICATION SLAVE ON *.* TO 'repl'@'%';
# 备库指向主库
CHANGE MASTER TO
MASTER_HOST='主库IP',
MASTER_USER='repl',
MASTER_PASSWORD='强密码',
MASTER_AUTO_POSITION=1;
START SLAVE;
# 检查同步状态
SHOW SLAVE STATUS\G
# 关键看这两个:Yes Yes
# Slave_IO_Running: Yes
# Slave_SQL_Running: Yes
Seconds_Behind_Master 是延迟秒数,正常应该是 0 或个位数。延迟大了查网络和备库性能。
健康检查脚本:自动发现,别自动切换
#!/bin/bash
# health-check.sh:每分钟跑一次,连续 3 次失败才判定
URL="http://主库IP/health"
fail=0
for i in 1 2 3; do
curl -sf --max-time 5 $URL > /dev/null || fail=$((fail+1))
sleep 10
done
if [ $fail -eq 3 ]; then
echo "主库连续3次健康检查失败" | mail -s "容灾告警" [email protected]
fi
注意两点:一是 /health 要真的检查业务(连一下数据库,返回 200 才算健康),只检查"ping 得通"不够——机器活着、业务死了,是最常见的"假活";二是只告警、不自动切换,切换按钮留在人手里。自动切换最怕误判:网络抖动一下,两边都觉得自己是主,数据写散了(脑裂),比停机更惨。
脑裂:最可怕的故障
脑裂 = 主备同时认为自己是主,同时写数据。恢复时两边数据对不上,神仙难救。预防:
- 切换前确认主库真的死了(多路检查:本机、外网、商家面板)
- 主库恢复后,先当备库同步,别直接写
- 业务允许的话,切换期间短暂只读,等确认再放开写
演练剧本
每季度一次,按这个剧本走:
时间:周日 03:00(低峰)
1. 03:00 宣布演练开始,业务切维护页(可选)
2. 03:05 模拟主库故障(停服务)
3. 03:06 按 checklist 切换到备库
4. 03:15 验证业务正常,记录 RTO
5. 03:20 检查数据:备库和主库差多少,记录 RPO
6. 03:30 切回主库,恢复正常
7. 整理演练报告:哪里卡了,下次改进
第一次演练一定超时,这很正常。演练三次后,RTO 会稳定在一个可预期的数字。
小够的最终建议
容灾是个光谱,不是非黑即白:
- 备份做好(人人都要)
- 文档写好(切换 checklist)
- 主备搭起来(停不起的业务)
- 演练跑起来(搭了不练等于没搭)
一步一步来,别想着一次到位。先把第 1、2 步做到位,已经超过 90% 的个人站长了。
DNS 服务商的选择
DNS 切换是容灾的核心环节,DNS 服务商得靠谱:
- 生效速度:改记录后全球生效要多久,TTL 设小是前提,服务商本身的推送速度也有差异
- API 支持:故障时手动改太慢,有 API 就能写脚本自动切(配合健康检查)
- 监控联动:有些 DNS 服务商自带健康检查,机器挂了自动切记录,连脚本都不用写
小够的建议:DNS 别用域名注册商送的免费版,找个专业的。TTL 300 秒是底线,平时就这么设着。
切换后的 DNS 传播
# 从多个地点查 DNS,看切换进度
dig @8.8.8.8 yourdomain.com +short
dig @1.1.1.1 yourdomain.com +short
不同地区的生效时间不一样,盯着看,别假设"改了就全生效了"。
数据一致性:切换时最痛的部分
主备切换必然丢一点数据(主从延迟那几秒),怎么办:
- 接受它:RPO 就是干这个的,提前和业务方对齐"最多丢 X 秒数据"
- 减小它:主从延迟平时就监控,延迟大了先优化,别等故障时才发现延迟 10 分钟
- 记录它:切换后记下"大约丢了 X 分钟的数据",事后对账用
电商订单这种,丢几秒可能是真金白银。RPO 定 1 小时的业务,和 RPO 定 1 分钟的业务,架构完全不是一个级别——先定 RPO,再定架构。
小够的实话
说实话,个人站长做主备,90% 的时间备机都在闲置,心理上会觉得"浪费钱"。算笔账:备机一台便宜 VPS,一年几百块;真出一次故障,手动恢复+数据丢失+用户流失,损失只多不少。
但反过来,为了"万一"过度投入也是浪费。判断标准就一条:这业务停 4 小时,你心疼吗?心疼就做,不心疼就把备份做好。够用就好,容灾也一样。
切换演练记录表
每次演练填一张表,贴在文档里:
演练日期:2025-XX-XX
场景:模拟主库宕机
开始时间:03:00
业务恢复时间:03:12 → RTO 12 分钟(目标 60 分钟,达标)
数据丢失:约 2 分钟 → RPO 2 分钟(目标 5 分钟,达标)
发现的问题:
1. 备机上有个服务没设开机自启,手动起的
2. DNS 生效比预期慢,某地区 20 分钟才切过来
改进:
1. 备机服务全部 systemctl enable
2. 换 DNS 服务商 / 接受现实
演练记录是容灾方案的"体检报告",一年攒四张,方案越来越靠谱。
多云容灾:要不要跨商家
主备在不同商家,优点是商家级故障也不怕,缺点是网络延迟大、同步慢、成本高。
小够的建议:先同商家不同机房,跑顺了再考虑跨商家。跨商家是"进阶版",别第一步就上难度。记住:能稳定跑起来的简单方案,胜过跑不起来的完美方案。
容灾和备份的关系
最后再理一遍两者的关系:
- 备份:数据丢了,找回来。RTO 长(几小时),RPO 取决于备份频率
- 容灾:机器挂了,业务不停。RTO 短(几分钟),RPO 取决于同步延迟
- 关系:容灾不能替代备份。备机也可能丢数据(误删、逻辑错误会同步过去),备份是最后一道防线
备份是 1,容灾是后面的 0。没有 1,再多 0 都是 0。
给不同规模的建议
| 规模 | 方案 |
|---|---|
| 个人博客 | 备份做好,容灾不需要 |
| 小电商/接单 | 备份 + 文档化的手动切换流程 |
| 日活上万的业务 | 主备 + 自动健康检查 + 季度演练 |
| 再大 | 请专职运维,别看博客了 |
对号入座,够用就好。容灾做到"匹配业务规模",就是最好的容灾。