移除 API 扩展支持

https://blueprints.launchpad.net/nova/+spec/api-no-more-extensions

在很久很久以前,OpenStack 最初由两项服务组成:Swift 和 Nova。最初的架构和计划是 Nova 作为单体云资源管理器。云中资源管理的所有工作都将通过 Nova 和 Nova API 完成。为了支持实验和扩展此范围,Nova API 被设计为具有外部化扩展机制,允许任何人添加新的资源,甚至修改现有的资源(如服务器/规格)。

但情况发生了变化。云资源管理的范围显然无法包含在一个项目中。OpenStack 开始拆分为一组通过文档化的 REST API 调用相互通信的微服务。Nova 和其他服务开始通过 API 暴露管理功能(而不仅仅是通过直接的数据库操作命令)。现在,添加新功能可以通过添加新服务来完成,而不是将代码侧载到 Nova 本身。随着 Big Tent 的创建,这些额外的服务现在可以很容易地找到一个协作和蓬勃发展的家园。

在野外的数千个 OpenStack 云中,互操作性是 OpenStack 长期成功的关键价值。它使消耗标准 OpenStack API 的应用程序生态系统蓬勃发展,从而进一步扩展 OpenStack 生态系统。

Nova 团队多年来一直在努力移除 API 中的扩展机制,以支持这一互操作性目标,并大大简化 Nova 代码库,使其更容易随着时间的推移添加新功能。本规范旨在作为历史和架构文档,明确说明这意味着什么。

问题描述

Nova API 扩展框架鼓励在部署 Nova 时采取所有错误的行为。它带来了大量的复杂代码债务,很少有人理解,并且要求 Nova 不使用任何标准的 wsgi 框架。它鼓励人们将新资源添加到 Nova,脱离树结构,而不是围绕 Nova 中的通用结构或通用的独立服务进行协作。它劝阻人们参与关于 API 更改的 upstream 对话,因为他们可以选择稍后关闭这些更改。更糟糕的是,它很容易更改核心对象,如服务器或规格,并更改其行为和表示形式。

在微版本发布之前,扩展机制被用作树结构中一个非常糟糕的版本控制机制,这导致了扩展之上扩展之上扩展的模型,试图以某种方式使 API 可发现。我们四轮之前改变了策略,并构建了一个显式的版本控制机制。

用例

作为多个 OpenStack 云的消费者,我希望软件在它们之间以相同的方式工作,并且不必预测 API 扩展带来的 API 更改。

作为 OpenStack 的开发人员,我希望 API 代码易于理解,以便很容易确保未来的更改不会破坏现有用户。

作为 OpenStack 应用程序的创建者,我希望 OpenStack 的 API 趋同,以便我的 OpenStack 应用程序可以在公共和私有云中广泛使用。

提议的变更

Nova API 扩展机制将在 Ocata 结束时完全移除。

在 Liberty 中,我们弃用了 API 扩展的概念,并将其从文档中移除 - https://docs.openstack.org/developer/nova/stable_api.html。在 Liberty 中,我们还弃用了 v2 遗留代码堆栈的使用(大多数扩展都是针对它编写的)。这是试图阻止 OpenStack 生态系统的新成员使用扩展。

在 Mitaka 中,我们弃用了 v2.1 API 中的配置选项,这些选项允许基于配置控制加载哪些扩展。这是该方向的另一个信号。

在 Newton 中,我们删除了 v2 遗留代码堆栈,导致净减少了 15KLOC 的相当晦涩的代码。我们删除了允许基于配置修改扩展加载的配置选项,这大大简化了所有 API 文档,并使能够开始将需要数百行代码才能添加单个属性的扩展折叠回去。然而,这仍然使 stevedore 配置可用以侧载代码(尽管这不受支持)。

在 Newton 中,我们将消除 stevedore 加载修改现有资源(服务器/规格)的扩展的能力,并开始将这些扩展折叠回核心服务器/规格代码中。这将大大简化 API 代码堆栈和测试,并使未来的添加更容易。我们将移除资源修改的预处理/后处理机制。

这将有效地忽略 “nova.api.v21.extensions.server.*” 扩展的内容,并移除扩展用于修改 API 其他部分的请求/响应的 @wsgi.extends 机制。

在 Ocata 中,我们将消除对 “nova.api.v21.extensions” stevedore 钩子的使用。这推迟到 Ocata 主要是因为移除 extends 机制优先级更高,并且根据我们目前的工作,在 Newton 中达到这个目标是不现实的。

备选方案

我们可以保持现状。然而,这一直是 Nova 标准化的长期方向。

扩展所有者的替代方案

我们知道,即使我们一直在长时间敲响去除扩展机制的鼓声,仍然有一些人拥有遗留扩展,或者尚未迁移到新模型。以下是建议的后续步骤。

将您的需求 upstream

将您的需求带到 upstream 社区。我们现在已经建立了一个完善的机制来添加 API 功能,并且自其 inception 以来,每个发布版本都已着陆大约 10 个微版本。如果对资源模型的更改确实需要暴露在服务器或规格上,那应该是一个 upstream 对话。这也意味着它将由更大的社区在未来维护(并且将使其与新的基础设施,如 Cells v2 一起工作)。

构建新服务

如果您只是使用扩展机制将全新的资源添加到 Nova,那么可以很容易地在具有新端点的全新服务中完成。如果这些资源引用服务器,可以使用 Nova API 调用检查这些服务器的有效性,就像 Neutron / Nova / Cinder 相互通信一样。

如果 Nova 数据模型中有额外的元素需要通过 API 或通过通知暴露,请将这些元素带到 upstream 社区。

但是我的扩展非常特定于我的环境

请无论如何将对话带到更广泛的社区。有很多 OpenStack 部署,您认为特定于您环境的问题可能并非如此。并且与 upstream 操作员和开发人员社区进行对话,我们可能可以提出一个支持您使用的通用机制。即使这只是添加额外的 URL 大小字段,允许引用其他服务。

数据模型影响

无。这仅仅是关于 API 堆栈中的表示层。

REST API 影响

REST API 本身不会更改,但是 REST API 的管道将得到极大的简化。

安全影响

唯一的安全影响在于策略的使用。以前,即使该扩展仅仅添加了服务器结构中的单个显示属性,也会为每个扩展制定一个策略点。这些策略规则将被大量移除,并且每次移除都将包含发布说明。当我们似乎正在暴露敏感元素时,将做出判断,并在那些情况下,我们将保留对其进行一些策略控制。

通知影响

无。

其他最终用户影响

Nova API 的更可靠的契约,以及使用它时可以期望什么。

性能影响

资源处理的简化可能会提高 API 的性能。但是,性能不是这里的首要驱动因素。

其他部署者影响

部署者影响如上所述。

开发人员影响

这将大大降低理解和贡献 Nova 中 API 层的门槛。

实现

负责人

Nova API 子团队

工作项

Newton

  • 将树内服务器扩展折叠回主 servers.py 流程(难点在于让单元测试通过)

  • 移除服务器资源上的 wsgi.extends 支持

  • 移除加载 nova.api.v21.extensions.server.* 内容

  • 将树内规格扩展折叠回主 flavors.py 流程

  • 移除规格上的 wsgi.extends 支持

  • 移除 wsgi 堆栈中的 pre_process / post_process 资源逻辑

Ocata

  • 移除加载 nova.api.v21.extensions(这些允许创建新资源,即使它们无法修改现有资源)。

依赖项

测试

Tempest 和功能测试都不需要进一步的更改。它们可以保证我们没有回归我们的 API。

单元测试将进行调整,因为在许多情况下,它们使用了有限的扩展列表来简化测试的响应。

文档影响

文档大多已经反映了这种现实。我们不再公开谈论 Nova 中的扩展机制。

参考资料

历史

修订版

发布名称

描述

Newton

引入