L3/BGP - 使 BGP 扬声器对基础设施中断具有弹性¶
https://bugs.launchpad.net/neutron/+bug/2006145
本 RFE 旨在为 BGP 扬声器建立的 BGP 对等会话实现弹性支持。目前,Neutron 动态路由服务架构依赖于 DRAgent 服务和 Neutron 服务器之间进行某种类型的消息传递。然而,这些通信严重依赖于消息传递服务的可用性(例如 RabbitMQ),OpenStack 基础设施节点中的任何瞬态/永久性故障都可能影响通过 BGP 的前缀通告。
问题描述¶
当我们在使用动态路由和 BGP 来通告云基础设施中的网络地址前缀时,所有网络流量都依赖于 BGP 对等元素的正确运行。DRAgent 在这种情况下起着至关重要的作用,因为该服务负责在南北通信中通告所有 L3 前缀,是云操作的单一漏洞点。
当前的 DRAgent 参考设计 [1] 使用如下所述的两个独立的周期性任务
状态报告周期性任务 (DrAgentWithStateReport 类)
+------------------------------------------------+
|DrAgentWithStateReport class |
| |
| +------------------------------------+ |
| |heartbeat = _report_state | |
| |interval=CONF.AGENT.report_interval | |
| | call _report_state | |
| +------------------+-----------------+ |
| | |
| +------------------+-----------------+ |
| |_report_state polling task | |
| | | |
| | RPC processing | |
| | if agent_status == revived | |
| | call schedule_full_resync | |
| +------------------+-----------------+ |
| | |
| +------------------+-----------------+ |
| |schedule_full_resync | |
| +------------------------------------+ |
| |
+------------------------------------------------+
BGP DRAgent 周期性任务 (BgpDrAgent 类)
+---------------------------------------+
|BgpDrAgent class |
| |
| +-------------------------------+ |
| |periodic_resync polling task | |
| |interval=CONF.periodic_interval| |
| | call _periodic_resync_helper | |
| +---------------+---------------+ |
| | |
| +---------------+---------------+ |
| |_periodic_resync_helper | |
| | if full_sync or resync/reason | |
| | call sync_state | |
| +---------------+---------------+ |
| | |
| +---------------+---------------+ |
| |sync_state | |
| | | |
| | if bgp_speaker_id == None | |
| | remove speaker from DRAgent | |
| | | |
| | Exception (MessagingTimeout) | |
| | call schedule_full_resync | |
| +--------------+----------------+ |
| | |
| +--------------+----------------+ |
| |schedule_full_resync | |
| +-------------------------------+ |
| |
+---------------------------------------+
这两个周期性任务具有独立配置的 interval 范围,BGP DRAgent 任务的 periodic_interval,以及心跳报告状态的 AGENT.report_interval。然而,来自这两个周期性任务都可以发起完全同步请求,并且将处理 sync_state 方法。RPC 心跳响应中的 agent_status revived 会激活上述整个流程,直到扬声器从 DRAgent 中移除。对于 sync_state 方法中发生 exception 的情况,将安排一次完全同步(根据上述描述的流程),直到扬声器从 DRAgent 中移除。
无论完全同步请求的来源如何,缓存机制显然不起作用,因为代理之前已经配置好,但在通过 RPC 接收到 revived 状态后,它只是从 DRAgent 中移除扬声器,并重新安排未来的同步,以便稍后重新包含(具体取决于配置的周期性间隔)。当扬声器从 DRAgent 中移除时,BGP 对等会话将被关闭,只有在扬声器重新添加后才会重新建立。
这个问题可以以两种不同的方式表现出来
当消息传递服务/RabbitMQ 离线并且在很长的时间间隔内没有响应 AMQP 服务器不可达(请注意 Neutron agent_down 配置的超时时间);然后 RMQ/RPC 再次变为活动状态。
当消息传递服务/RabbitMQ 队列承受很大的压力和/或遇到 exception 超时,例如:等待回复超时;然后 RMQ/RPC 再次变为活动状态。
提议的变更¶
为了解决上述问题,建议为 DRAgent 引入新的扬声器缓存逻辑,以便在 RPC 异常和/或通过 RPC 重新建立通信的情况下保留扬声器设置和 BGP 对等会话。此外,为了避免由于 RPC 通信中的瞬态故障而从 DRAgent 中移除 BGP 扬声器配置,需要更改 get_bgp_speakers 空返回处理逻辑,首先安排一次完全同步,然后在下一次周期性同步中允许移除 BGP 扬声器。
为了启用新的 DRAgent 扬声器缓存机制,应通过 bgp_dragent.ini 文件中的 [BGP] 部分启用一个新的配置选项。
* ``speaker_cache_timeout = 300``
此配置选项使 DRAgent 能够在配置的超时时间(以秒为单位)内保留扬声器设置和相关的 BGP 对等会话。此超时缓存的目的是防止 resync 检查逻辑中的错误,从而在满足超时条件之前不会移除任何扬声器。
speaker_cache_timeout 的默认值必须为零,从而保持当前的 DRAgent 行为。任何非零值都应影响 DRAgent 行为,如下所述
状态报告周期性任务:使用 revived RPC 状态,DRAgent 必须启动缓存超时计时器,并将 cache_out_of_sync 标志设置为 True。如果 DRAgent 在 cache_out_of_sync 变为 False 之前执行 sync_state 方法,则必须忽略完全同步过程,并等待下一次周期性检查。
DRAgent 周期性任务:如果 sync_state 方法在操作期间抛出任何 exception,DRAgent 必须启动缓存超时计时器,并将 cache_out_of_sync 标志设置为 True。与上述情况类似,如果 DRAgent 在 cache_out_of_sync 变为 False 之前执行 sync_state 方法,则必须忽略完全同步过程,并等待下一次周期性检查。
缓存超时任务:如果在计时器计数期间发生另一个 revived 或 Exception 事件,缓存任务必须重置超时间隔计数并重新开始。否则,缓存任务必须在配置的超时到期时终止,并将 cache_out_of_sync 标志设置为 False。
默认工作流程:如果 speaker_cache_timeout 为空或设置为零;或者如果配置的缓存超时计时器已到期 - cache_out_of_sync 标志为 False;任何周期性任务都应运行完全同步。
数据库影响¶
无
Rest API 变更¶
无
实现¶
负责人¶
主要负责人:Roberto Bartzen Acosta <rbartzen@gmail.com>
工作项¶
在 DRAgent 扬声器同步中实现新的缓存逻辑。
使用 Neutron 动态路由中现有的设施实现相关的单元和功能测试。
编写文档。
文档影响¶
用户文档¶
有关 DRAgent 扬声器缓存支持的信息。
测试¶
单元/功能测试。