最近在测试 Keepalived 时,发现按照默认配置配好 VRRP 协商成功,Master 节点也正常配置了 VIP,但是外部 ping 不通,服务也无法访问。后来查找一些文档,发现和 vrrp_strict 模式有关。

环境信息:

Keepalived:v2.2.4 (08/21,2021)


问题根源

默认情况下 keepalived.conf 中会启用 vrrp_strict 模式,该配置会导致 VIP 不处理发给其的请求。

在 Master 抓包结果如下,能收到来自外部发给 VIP 的请求,但是没有回应:

Keepalived 配置完成后 VIP ping 不通的解决方案_不响应请求

正常响应对比:

Keepalived 配置完成后 VIP ping 不通的解决方案_不响应请求_02


vrrp_strict 模式说明

Keepalived 基于 vrrp 来实现网关高可用,但会有一些自己的私有实现,为了保证 Keepalived 完全兼容 vrrp 协议,引入了 vrrp_strict 这一模式。

开启此模式后,Keepalived 下列配置会被禁止:

  • 0 VIP(未配置 VIP)
  • 单播邻居
  • vrrp_version 为 2 时使用 IPv6 地址
  • 认证(可以配置,但不生效)

除了上述三个点,开启 vrrp_strict 还会导致不接受发给 VIP 的请求,除非:

  • vrrp 优先级为 255,这时 VIP 就可以接受流量
  • vrrp_version 为 3 时,支持设置 Accept_mode(vrrp3 的一个功能),这时就允许 VIP 接受流量

所以解决办法就是对症下药,总共有三种方式:


解决方法1:关掉 vrrp_strict 模式

简单粗暴的一种办法,禁用 vrrp_strict 模式,配置示例如下:

Keepalived 配置完成后 VIP ping 不通的解决方案_vrrp_03

Keepalived 配置完成后 VIP ping 不通的解决方案_vrrp_04

启用服务后完整的主节点日志如下(journalctl -f -u keepalived):

Keepalived 配置完成后 VIP ping 不通的解决方案_LVS_05

备节点日志:

Keepalived 配置完成后 VIP ping 不通的解决方案_不响应请求_06

外部客户端访问 VIP 时,主节点响应请求:

Keepalived 配置完成后 VIP ping 不通的解决方案_不响应请求_07


解决方法2:使用 vrrp v3 + accept 模式

配置示例如下:

Keepalived 配置完成后 VIP ping 不通的解决方案_keepalived_08

主节点日志如下:

Keepalived 配置完成后 VIP ping 不通的解决方案_LVS_09

备节点日志:

Keepalived 配置完成后 VIP ping 不通的解决方案_keepalived_10


解决方法3:vrrp 优先级使用 255

这种模式并不推荐,因为需要每个节点都是用 255 的优先级,不能固定主备状态。

配置方式如下:

Keepalived 配置完成后 VIP ping 不通的解决方案_vrrp_11

在测试中会发现,一开始 keepalived1 节点成为了主,但一旦 Keepalived2 上线,日志会提示优先级一致,Keepalived2 又成为了主:

Keepalived 配置完成后 VIP ping 不通的解决方案_keepalived_12

虽然故障切换正常,但生产环境还是尽量不要这样配置。


参考文档:

https://manpages.debian.org/stretch/keepalived/keepalived.conf.5.en.html

https://askubuntu.com/questions/1312333/keepalived-not-working-on-20-04