1. 为什么需要Keepalived?
在分布式系统中,高可用性是最核心的需求之一。想象一下,当你的主服务器突然宕机,整个服务就完全不可用了,这显然是不可接受的。Keepalived就是为了解决这个问题而生的。
Keepalived是一个基于VRRP协议实现的高可用解决方案。VRRP(Virtual Router Redemption Protocol)虚拟路由冗余协议,它能够将多个物理服务器虚拟成一个虚拟服务器,对外提供一个虚拟IP(VIP)。当主服务器出现故障时,备服务器会自动接管VIP,实现无缝切换。
提示:VRRP协议默认使用224.0.0.18作为组播地址,端口号为112。了解这一点对后续的防火墙配置很重要。
在实际生产环境中,Keepalived最常见的应用场景包括:
- Web服务器负载均衡和高可用
- MySQL主从切换
- Nginx反向代理集群
- 各种需要IP漂移的场景
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 环境准备与安装
2.1 系统要求
Keepalived对系统要求不高,但为了最佳性能,建议:
- Linux内核版本2.6.13及以上
- 至少1GB内存(生产环境建议4GB以上)
- 两个或更多网络接口(用于主备切换)
我个人的经验是,在CentOS 7/8或Ubuntu 18.04/20.04上运行效果最好。下面以CentOS 7为例说明安装过程。
2.2 安装步骤
对于大多数Linux发行版,安装Keepalived都非常简单:
bash复制# CentOS/RHEL
sudo yum install -y keepalived
# Ubuntu/Debian
sudo apt-get install -y keepalived
如果你想从源码编译安装(比如需要特定版本或自定义功能):
bash复制wget https://www.keepalived.org/software/keepalived-2.2.4.tar.gz
tar zxvf keepalived-2.2.4.tar.gz
cd keepalived-2.2.4
./configure --prefix=/usr/local/keepalived
make && make install
注意:源码安装后需要手动配置systemd服务文件,这是很多新手容易忽略的地方。
2.3 防火墙配置
Keepalived依赖VRRP协议通信,必须确保防火墙允许相关流量:
bash复制# 允许VRRP组播
sudo firewall-cmd --add-rich-rule='rule protocol value="vrrp" accept' --permanent
sudo firewall-cmd --reload
# 或者更精确地指定
sudo firewall-cmd --add-rich-rule='rule family="ipv4" source address="192.168.1.0/24" protocol value="vrrp" accept' --permanent
3. 核心配置文件详解
Keepalived的主配置文件通常位于/etc/keepalived/keepalived.conf。这个文件采用分段式结构,主要包含三大块:
3.1 全局定义块(global_defs)
conf复制global_defs {
notification_email {
admin@example.com
backup@example.com
}
notification_email_from keepalived@example.com
smtp_server 127.0.0.1
smtp_connect_timeout 30
router_id LVS_DEVEL # 唯一标识,建议使用主机名
}
这部分配置虽然看起来简单,但有几个关键点:
- router_id必须唯一,否则会导致脑裂问题
- 邮件通知在生产环境中非常有用,但需要正确配置SMTP服务器
- 我建议至少配置两个通知邮箱,避免单点故障
3.2 VRRP实例配置
这是Keepalived最核心的部分:
conf复制vrrp_instance VI_1 {
state MASTER # 初始状态,BACKUP表示备机
interface eth0 # 绑定的网卡
virtual_router_id 51 # 必须相同的一组实例
priority 100 # 优先级,MASTER应该比BACKUP高
advert_int 1 # 检查间隔,单位秒
authentication {
auth_type PASS
auth_pass 1111 # 密码,建议修改
}
virtual_ipaddress {
192.168.1.100/24 dev eth0 label eth0:1
}
track_script {
chk_nginx # 自定义的健康检查脚本
}
}
关键参数说明:
- virtual_router_id:范围1-255,同一组实例必须相同
- priority:范围1-254,值越大优先级越高
- advert_int:通常1秒足够,网络不稳定时可适当增大
3.3 健康检查配置
Keepalived支持多种健康检查方式,最常用的是脚本检查:
conf复制vrrp_script chk_nginx {
script "/etc/keepalived/check_nginx.sh"
interval 2 # 检查间隔
weight -20 # 检查失败时优先级降低值
fall 2 # 连续失败多少次认为服务不可用
rise 2 # 连续成功多少次认为服务恢复
}
一个简单的Nginx检查脚本示例:
bash复制#!/bin/bash
if [ $(ps -ef | grep -v grep | grep nginx | wc -l) -eq 0 ]; then
exit 1
else
exit 0
fi
记得给脚本执行权限:
bash复制chmod +x /etc/keepalived/check_nginx.sh
4. 高级配置与优化
4.1 多VIP配置
一个Keepalived实例可以管理多个VIP:
conf复制virtual_ipaddress {
192.168.1.100/24 dev eth0 label eth0:1
192.168.1.101/24 dev eth0 label eth0:2
10.0.0.100/24 dev eth1 label eth1:1
}
4.2 抢占模式控制
默认情况下,当MASTER恢复后会重新抢占VIP。可以通过nopreempt禁用:
conf复制vrrp_instance VI_1 {
...
nopreempt
preempt_delay 300 # 抢占延迟,单位秒
}
4.3 日志配置
Keepalived日志默认输出到系统日志(/var/log/messages),可以单独配置:
conf复制global_defs {
...
log_file /var/log/keepalived.log
log_facility local0
}
然后在/etc/rsyslog.conf中添加:
conf复制local0.* /var/log/keepalived.log
重启rsyslog生效:
bash复制systemctl restart rsyslog
5. 常见问题排查
5.1 脑裂问题(Split-Brain)
这是Keepalived最危险的问题,表现为两个节点都认为自己是MASTER。解决方法:
- 检查virtual_router_id是否冲突
- 检查防火墙是否阻止了VRRP通信
- 确保网络连接稳定,特别是心跳线
- 可以配置unicast_peer指定对端IP
conf复制vrrp_instance VI_1 {
...
unicast_src_ip 192.168.1.10 # 本机IP
unicast_peer {
192.168.1.11 # 对端IP
}
}
5.2 VIP不漂移
当主节点宕机但VIP没有转移到备节点时:
- 检查备节点的priority是否设置正确
- 检查健康检查脚本是否返回正确状态码
- 使用tcpdump检查VRRP报文:
bash复制tcpdump -i eth0 vrrp -n
5.3 服务启动失败
常见错误及解决方法:
- "VRRP: Can't add multicast route":通常是因为网络接口名称不对
- "IPVS: Can't initialize ipvs":需要加载ip_vs模块
bash复制modprobe ip_vs
echo "ip_vs" >> /etc/modules-load.d/ip_vs.conf
6. 生产环境最佳实践
经过多年运维经验,我总结了以下Keepalived使用建议:
- 网络分离:最好使用独立的心跳网络(直连或专用VLAN)
- 监控配置:监控Keepalived进程和VIP状态
- 版本选择:生产环境建议使用稳定版(目前是2.2.x系列)
- 安全加固:
- 修改默认的auth_pass
- 限制VRRP通信的源IP
- 禁用不必要的脚本执行权限
- 测试方案:定期进行故障转移测试
一个完整的生产级配置示例:
conf复制global_defs {
router_id web-proxy-01
enable_script_security
script_user root
}
vrrp_script chk_nginx {
script "/usr/local/bin/check_nginx.sh"
interval 3
weight -30
fall 3
rise 2
timeout 5
user root
}
vrrp_instance VI_WEB {
state BACKUP
interface eth0
virtual_router_id 51
priority 100
advert_int 2
nopreempt
authentication {
auth_type PASS
auth_pass Zx8$kL2p
}
virtual_ipaddress {
192.168.1.100/24 dev eth0 label eth0:1
}
track_script {
chk_nginx
}
notify_master "/usr/local/bin/notify.sh master"
notify_backup "/usr/local/bin/notify.sh backup"
notify_fault "/usr/local/bin/notify.sh fault"
}
7. 与其他工具的集成
7.1 与Nginx/LVS集成
Keepalived最初是为LVS设计的,与Nginx配合也非常常见:
conf复制virtual_server 192.168.1.100 80 {
delay_loop 6
lb_algo rr
lb_kind DR
persistence_timeout 50
protocol TCP
real_server 192.168.1.10 80 {
weight 1
TCP_CHECK {
connect_timeout 3
nb_get_retry 3
delay_before_retry 3
connect_port 80
}
}
real_server 192.168.1.11 80 {
weight 1
TCP_CHECK {
connect_timeout 3
nb_get_retry 3
delay_before_retry 3
connect_port 80
}
}
}
7.2 与Docker/Kubernetes集成
在容器环境中使用Keepalived需要注意:
- 需要将网络模式设为host
- 或者使用macvlan/ipvlan网络驱动
- 在K8s中可以考虑使用kube-keepalived-vip这样的专门方案
一个Docker运行的例子:
bash复制docker run -d --name keepalived --net=host \
-v /path/to/keepalived.conf:/etc/keepalived/keepalived.conf \
osixia/keepalived:2.2.4
8. 性能调优与监控
8.1 性能参数调整
conf复制global_defs {
vrrp_garp_master_refresh 60 # MASTER发送GARP报文的间隔
vrrp_garp_master_repeat 2 # 每次发送的GARP报文数量
vrrp_version 3 # 使用VRRPv3协议
}
vrrp_instance VI_1 {
garp_master_delay 10 # 成为MASTER后延迟发送GARP
garp_lower_prio_delay 10 # 优先级降低后延迟发送GARP
}
8.2 监控方案
建议监控以下指标:
- Keepalived进程状态
- VIP当前所在节点
- VRRP报文收发情况
- 健康检查脚本执行结果
可以使用Prometheus的keepalived-exporter,或者在Zabbix中配置自定义监控项。
一个简单的监控脚本示例:
bash复制#!/bin/bash
# 检查Keepalived进程
if ! pgrep -x "keepalived" > /dev/null; then
echo "Keepalived process not running"
exit 1
fi
# 检查VIP是否存在
VIP="192.168.1.100"
if ! ip a | grep -q "$VIP"; then
echo "VIP $VIP not found"
exit 1
fi
echo "Keepalived status OK"
exit 0
在实际部署中,我发现很多问题都源于基础配置错误。比如有一次,客户反映VIP切换后服务仍然不可用,最后发现是因为新主节点上的服务没有监听0.0.0.0,只绑定了具体IP。这种细节问题往往最容易被忽视,但却能导致整个高可用方案失效。
