跳转到: 导航, 搜索

Sahara/NextGenArchitecture

目前 Sahara 是一个在单个 Python 进程中运行的单一服务。所有的 REST API、数据库交互、配置机制都在一起工作。这在集群创建时产生很多高 I/O 负载的问题,以及缺乏高可用性等。

应该有两个阶段来改进 Sahara 架构。

阶段 1:将 Sahara 分解为不同的服务

Sahara 应该被分解为两个可水平扩展的服务

  • sahara-api (s-api);
  • sahara-engine (s-engine)。

此外,数据库访问层应该从主代码中解耦为 'conductor' 模块

在这个阶段,应该解决以下问题

  • 解耦 UI 和配置
    • 即使配置部分完全繁忙,UI 也应该具有响应性;
  • 启动大型集群
    • 需要使用多个引擎来配置一个 Hadoop 集群;
    • 将集群创建分解为许多原子任务;
    • 非常重要的是支持从多个引擎并行 ssh 到许多节点;
  • 一次启动多个集群
    • 需要利用多个进程;
    • 需要利用多个节点;
  • 长期运行的任务
    • 我们应该避免在一个引擎上等待很长时间,以最大限度地降低中断风险;
  • 新的配置插件 SPI
    • 它应该使插件的配置更容易;
    • 它应该生成可以同时执行的任务;
  • 支持 EDP
    • 它需要长期运行的任务;
    • Sahara 应该支持同时运行多个任务(一个集群上的多个作业);
    • 还有其他?


接下来的几个部分解释了建议的 Sahara 服务含义和职责。


Savanna architecture draft.png


服务 sahara-api (s-api)

它应该是可水平扩展的,并使用 RPC 来运行任务。

职责

  • REST API
    • http 端点/方法验证;
    • 对象存在性验证;
    • 基于 jsonschema 的验证;
  • 插件或操作特定的验证
    • sahara 侧验证(例如,应该限制删除在其他模板或集群中使用的模板);
    • 要求插件验证操作;
  • 为操作创建初始任务;
  • 该服务将是 Sahara 的端点,应该在 Keystone 中注册,如果有很多 sahara-api,我们应该使用 HAProxy 作为端点,它将在多个 sahara-api 之间平衡负载;
  • 与 OpenStack 组件交互
    • 使用 Keystone 进行身份验证(未来我们需要采用 trust 或其他机制来支持长期运行的任务和自动扩展);
    • 使用 Nova、Glance、Cinder、Swift 等进行验证。

服务 sahara-engine (s-engine)

Sahara engine 服务应该执行任务并创建新的任务。它可以调用插件来完成某些操作。职责

  • 运行任务和长期运行的任务;
  • 与其它 OpenStack 组件交互
    • 使用 Nova、Glance、Cinder 创建不同的资源(实例、卷、IP 等)。

任务执行框架

我们应该创建任务执行框架的草案并实现它,以利用可水平扩展架构的优势。

用于讨论和起草它的 Etherpad:https://etherpad.openstack.org/savanna_tasks_framework

Conductor 模块

该模块应该负责与数据库交互并隐藏数据库,使其不被其他组件访问。

职责

  • 数据库交互;
  • 不与其它 Sahara 和 OpenStack 组件交互。

阶段 2:为配置任务实现高可用性

Sahara 中的所有重要操作都应该是可靠的,这意味着 Sahara 应该支持回放事务和回滚所有任务。这里有一个用于执行此操作的库 https://wiki.openstack.org/wiki/TaskFlow 在 stackforge 中。看起来它可以在 Sahara 架构改进的第二阶段中使用。为了解决可靠性和一致性问题,我们可能应该添加一个用于任务/工作流协调的 Sahara 服务 - sahara-taskmanager (s-taskmanager),它也应该是可水平扩展的。

在这个阶段,应该解决以下问题

  • 对工作流的支持;
  • 任务/工作流执行的可靠性;
  • 长期运行任务的可靠性。

主要操作执行流程

通用流程提示

  • DB 对象将仅在负责 DB 交互的模块 ('savanna/db/sqlalchemy') 中使用;
  • 所有与数据库相关的类的导入都应该位于此模块 ('savanna/db/sqlalchemy') 中;
  • 在 sahara-api 和 sahara-engine 中,我们将使用简单的资源对象(实际上是字典);
  • 待定 (TBD)。

创建模板

  • [s-api] 解析传入请求;
  • [s-api] 执行模式和基本验证;
  • [s-api:plugin] 执行模板的高级验证;
  • [s-api:conductor] 将模板存储在数据库中;
  • [s-api] 向用户返回响应。

启动集群

  • [s-api] 解析传入请求;
  • [s-api] 执行模式和基本验证;
  • [s-api:plugin] 执行集群创建的高级验证;
  • [s-api:conductor] 将集群对象存储在数据库中;
  • [s-api] 向用户返回响应;
  • [s-api] 调用 sahara-engine 启动集群;
  • [消息队列 / 本地模式];
  • [s-engine-1] 开始准备集群的基础设施;
  • [s-engine-1:plugin] 更新集群的基础设施需求(例如,添加管理节点,更新实例的一些属性,设置初始脚本等);
  • [s-engine-1] 启动任务以创建所有基础设施并等待其完成;
  • [消息队列 / 本地模式];
  • [s-engine-2 | s-engine-3 | s-engine-X] 从 MQ 运行任务,它可以创建实例并在其上运行命令,创建和附加 cinder 卷等;
  • [s-engine-1] 所有基础设施准备就绪,继续;
  • [s-engine-1:plugin] 通过为集群节点创建文件和脚本的任务来配置集群;
  • [消息队列 / 本地模式];
  • [s-engine-2 | s-engine-3 | s-engine-X] 从 MQ 运行任务,它可以上传文件、运行脚本等;
  • [s-engine-1:plugin] 启动任务以启动节点上所需的服务(集群启动);
  • [s-engine-2 | s-engine-3 | s-engine-X] 从 MQ 运行任务,它可以运行某些服务;
  • [s-engine-1:conductor] 更新集群状态;

扩展集群

与“启动集群”操作的行为相同。

附加说明

一体化安装

我们希望使 "savanna-all" 二进制文件支持一体化 Savanna 执行,用于小型 OpenStack 集群和开发/质量保证需求。

一些说明和常见问题解答

为什么不将配置代理部署到 Hadoop 集群以配置所有其他内容?

这种行为存在几个缺点

  • 在启动大型集群时,代理的扩展将存在问题;
  • 在集群扩展期间,我们可能会遇到代理迁移问题;
  • 代理是意外的实例资源消耗者(这可能会影响 Hadoop 配置);
  • 这些代理需要与所有其他服务通信(相同的消息队列,相同的数据库等),用户将能够登录到这些实例,因此这是一个安全漏洞;
  • 我们需要支持各种 Linux 发行版,以及不同的 python 和 lib 版本。

为什么现在不实现高可用性?

我们目前的主要重点是实现 EDP 并通过支持使用多个引擎来配置一个 Hadoop 集群和同时配置多个 Hadoop 集群来提高 Sahara 的性能。因此,我们希望将这项艰巨的工作分解为几个步骤并逐步进行。

为什么我们需要长期运行的操作?

有一些我们需要执行的长期运行的操作,例如,在减少集群大小时进行退役。

服务之间如何交互?

Oslo RPC 框架和消息队列(RabbitMQ、Qpid 等)将用于服务之间的交互。

确定架构升级成功的潜在指标

  • s-api
    • 每秒处理的请求数(每个请求组);
  • s-engine
    • 每个 Sahara 控制器同时启动的 Hadoop 集群数;
    • 在特定数量的控制器上使用特定数量的节点创建单个 Hadoop 集群的速度;
    • 具有特定数量节点的集群创建时间(不包括实例启动时间)。