Octavia 简介


Octavia is an open source, operator-scale load balancing solution designed to work with OpenStack.

自 Pike 以来 OpenStack 推荐使用 Octavia 代替 neutron-lbaas extension 作为 Load Balancing as a Service 的首选方案,并在 Queens 中将 neutron-lbaas 标记为废弃 —— Neutron-lbaas is now deprecated

社区推崇 Octavia 的原因有很多,它解决了 neutron-lbaas 遗留的历史包袱,能够对外提供独立而稳定的 API。简单的说,社区认为 neutron-lbaas 使 Neutron 的项目管理变得拖沓,LBaaS 应该作为一个独立项目得到长足的发展,事实也是如此。

《Octavia 分析与实现》系列基于 Rocky,主要记录、分析了 Octavia 作为 OpenStack LBaaS 的抽象设计,开发性设计及架构代码实现,从中感受社区开发者们对 Octavia 的寄予。

本文作为系列的开篇,希望能够从宏观的角度鸟瞰 Octavia 的全貌,由面及点,更利于后续理解 Octavia 的底层实现细节。

基本对象概念


LBaaS:对于 OpenStack  云平台而言,LB(负载均衡)被作为一种服务提供给用户,用户得以按需地获取可配置的业务负载均衡方案,这就是所谓 Load Balancing as a Service。

LoadBalancer:负载均衡服务的根对象,用户对负载均衡的定义、配置和操作都基于此。

VIP:与 LoadBalancer 关联的虚拟 IP 地址,每个 LoadBalancer 最起码有一个 VIP 作为外部对后端业务集群访问的标准入口。

Listener:下属于 LoadBalancer 的监听器,可配置监听外部对 VIP 的访问类型(e.g. 协议、端口)。

Pool:后端的真实业务云主机集群域,一般的,用户会根据云主机的业务类型进行划分。

Member:业务云主机,下属于 Pool,对应传统负载均衡体系中的 Real Server。

Health Monitor:挂靠于 Pool,周期性对 Pool 中的 Member(s) 进行健康检查。

L7 Policy:七层转发策略,描述了数据包转发的动作(e.g. 转发至 Pool,转发至 URL 或拒绝转发)。

L7 Rule:七层转发规则,下属于 L7 Policy,描述了数据包转发的匹配域(e.g. 转发至 Pool 中所有以 webserver 开头的 Members)。

图1. 动静分离负载均衡应用模型图

上图是一个简易的利用负载均衡实现的 Web 动静页面分离模型,辅助理解上述概念及其个体与整体间的关系。

基本使用流程


下面从使用的角度来感性了解 Octavia,首先介绍 Octavia 的网络结构。

图2. Octavia 网络架构图(注:图源来自孔令贤的博客)

标准的 Octavia 网络架构,包含了:

Amphora(e):实体为云主机,作为负载均衡器的载体,也是 Octavia 默认的 Loadbalancer Provider。

lb-mgmt-net:是一个与 OpenStack Management/API Network 打通的网络,admin project 可见,东侧连接 Amphora Instance、西侧连接 Octavia Services。

tenant-net:业务云主机所在的网络。

vip-net:提供 VIP 地址池的网络。

NOTE:其中 vip-net 和 tenant-net 可以是同一个网络,但在生产环境中,我们建议分开。这样更有利于针对性的施加安全策略,划分不同级别的网络安全隔离域。

图3. 初始的 OpenStack 网络拓扑图

在 Dashboard 创建一个 Loadbalancer 的步骤

  • Step 1. 设定 loadbalancer 的 VIP。支持直接指定 VIP,或由 DHCP 分配。

  • Step 2. 设定 listener 监听的协议及端口。监听 http://<VIP>:8080/ 的外部访问。

  • Step 3. 设定 pool 的负载均衡算法。这里选择 RR 轮询分发算法。

  • Step 4. 设定 pool 下属的 members。设定 members 需要指定端口和权重,前者组成了接受数据转发的 socket,后者表示分发的优先级。

  • Step 5. 设定 health monitor 的健康检查规则。如果 members 出现 PING 不同的情况,则会被标记为故障,不再接受分发。

创建完 lb-1 之后的网络拓扑变更如下图。可以看出,Amphorae 在之中起到了关键作用,使用端口挂载的方式将属于 3 个不同网络中的 VIP、Members 及 Octava Services 串连起来,Amphorae(双耳壶)也因此得名。

图4. 创建 LoadBalancer 之后的 OpenStack 网络架构图

现在,我们不妨粗浅的梳理一下 Octavia Amphora Provider 的设计思路:

  • Amphorae 作为负载均衡器软件(HAProxy)和高可用支撑(Keepalived)的运行载体,通过 Agent 与 Octavia Services 通信。
  • Octavia Services 接收到用户 Create LoadBalancer 和 VIP 的选项参数后,通知 Agent 动态变更 haproxy、keepalived 的配置文件。
  • 将 Members 所处的 Subnet 接入 Amphorae,内含的 haproxy 通过 Member Socket(IP, Port) 分发请求数据包。

图5. 简易的 Octavia 通讯模型

这里再补充一下与 Octavia 相关的 image 和 security group 的内容。Launch Amphora Instance 需要使用特定的镜像,Octavia 提供了专门的镜像制作工具。暂支持 CentOS 和 Ubuntu 两种操作系统,也支持设定 password,不过在生产环境中还是建议使用 keypair 进行登录。至于安全组,从图 5 可以看出 Amphora 的安全组最起码要满足 ingress:UDP/5555 和 egress:TCP/9443 两条规则。

 

使用 amphora image 的步骤

  • Step 1. 上传 amphora image

$ /opt/rocky/octavia/diskimage-create/diskimage-create.sh -i ubuntu

$ openstack image create amphora-x64-haproxy \

 --public \

 --container-format=bare \

 --disk-format qcow2 \

 --file /opt/rocky/octavia/diskimage-create/amphora-x64-haproxy.qcow2 \

 --tag amphora

 

  • Step 2. 配置使用 amphora image

[controller_worker]

amp_image_owner_id = <amphora-image id>

amp_image_tag = amphora

...

 

使用 amphora security group 的步骤

  • Step 1. 创建 amphora 使用的安全组

$ openstack security group create amphora-sec-grp --project <admin project id>

$ openstack security group rule create --remote-ip "0.0.0.0/0" --dst-port 9443 --protocol tcp --ingress --ethertype IPv4 --project <admin project id> amphora-sec-grp

$ openstack security group rule create --remote-ip "0.0.0.0/0" --dst-port 5555 --protocol udp --egress --ethertype IPv4 --project <admin project id> amphora-sec-grp

  • Step 2. 配置使用 amphora security group

[controller_worker]

amp_secgroup_list = <amphora-sec-grp id>

...

 

软件架构


图6. Octavia 架构图(注:图源自 Octavia 官方文档)

Octavia 的架构设计依旧是常规的「生产者-消费者」异步通讯模型,API 与 Worker 分离再通过 MessageQueens 进行通信。

  • Octavia API:标准 RESTful API,Octavia v2 API(default enabled)是 LBaaS v2 API 的超集,完全向后兼容。所以版本滞后的 OpenStack 平台也可通过 Neutron Octavia Driver 进行集成。
  • Octavia Controller Worker:Octavia 的核心,底层采用 Driver & Plugin 的设计来满足 OpenStack 平台所代表的开放性,支撑上层的 3 大功能模块。
    • Octavia Worker:负责完成 API 请求,是 Octavia 主干功能的执行者。
    • Health Manager:负责保证 LoadBalancer Provider 的高可用
    • Housekeeping Manager:名副其实的 Housekeeping(家政),保障 Octavia Services 清洁的运行环境。实现了 SpaceAmphora、DatabaseCleanup 和 CertRotation。

NOTE:需要特别说明的是,架构图中虽然只给出了 Amphora 一种 LB Provider,但 Drivers & Plugin 设计实际上是支持多种 LB Provider 的(e.g. F5)。社区一直有计划将这些已实现的 Drivers 从 openstack/neutron-lbaas repo 迁移到 openstack/octavia repo,只是一直很缺人手。

服务进程清单


Octavia Service Menu 是软件架构的具象表现:

  • octavia-api
  • octaiva-worker
  • octavia-health-manager
  • octavia-housekeeping

代码结构


下面列举一些关键的目录:

  • amphora:Amphora REST API 和 amphora-agent 的实现
  • api:Octavia API 的实现
  • certificates:CA 认证的实现,支持 Amphora 与 Octavia Controller Worker 间的安全通信以及 TLS 功能
  • compute:实现了 Compute Driver 的抽象和 novaclient 的封装
  • network:实现了 Network Driver 的抽象和 neutronclient 的封装
  • db:ORM 层的封装实现
  • policies:定义了 API 请求的鉴权策略

继续展开 controller 目录:

  • healthmanager:Health Manager 的实现
  • housekeeping Manager:HouseKeeping Manager 的实现
  • queue:内部 RPC 通信实现,应用了 cotyledon 框架和 oslo_messaging 库
    • api/handlers/queue/producer.py
    • controller/queue/consumer.py
  • worker:Octavia Worker 的实现,应用了 TaskFlow 框架
    • flows:任务流的封装,每个功能单元都会被定义为一个 Flow
    • tasks:任务的封装,使得任务的逻辑实现得以高度重用

PS:cotyledon 是由社区开发用于替代 oslo.service 的第三方开源库。

 

      Cotyledon provides a framework for defining long-running services. It provides handling of Unix signals, spawning of workers, supervision of children

     processes, daemon reloading, sd-notify, rate limiting for worker spawning, and more.

                                                                                                                                                                                                       —— 摘自 cotyledon 官方文档

最后简单终结一下 Octavia 的架构设计,作为独立项目,其继承了 OpenStack 一贯优秀的开放性,在 LB Provider、Certificates Driver、Compute Driver 和 Network Driver 这些外部支撑节点都高度抽象出了 Driver 类,使 Vendors 和 Users 得以简便接入现有的基础设施。这无疑是 Octavia 甚至 OpenStack 受到欢迎的原因之一。

下一篇《Octavia Rocky 的实现与分析系列二:创建 LoadBalancer 的流程》即将更新,敬请期待!