Glance Swift Store 使用多个容器存储镜像¶
https://blueprints.launchpad.net/glance/+spec/swift-store-multiple-containers
当 Glance 配置为在单租户模式下使用 Swift 存储时,镜像存储在一个容器中,如配置选项 swift_store_container 所指示。将镜像存储在一个容器中的这种方法容易受到性能瓶颈的影响。
将镜像存储在一个容器中容易受到 Swift 对容器的速率限制。Swift 配备了容器速率限制,可以限制单个容器中的并发 POST、PUT 和 DELETE 操作。这在大型部署中尤其成问题,尤其是在与较小的分段大小结合使用时。
问题描述¶
Swift 已知可以限制传入流量[1]。Swift 可以限制容器上的写操作的事实表明存在性能瓶颈,因此大型部署需要一种替代方案来规避 Swift 限制。
当为 Swift 集群启用容器速率限制时,它会在达到某个可配置的速率后限制并发 POST、PUT 和 DELETE 请求。这直接转化为 Glance 在体验性能下降之前并发镜像创建和删除操作的限制。
提议的变更¶
为了减少/克服性能瓶颈,我们建议在单租户模式下使用多个容器来存储镜像(此更改不会影响多租户模式,因为该设置将每个镜像存储在其自己的容器中)。这提高了镜像创建和删除操作的并发性。
此更改有四个主要方面
容器选择 - 确定镜像应该进入哪个容器
容器创建 - 创建新的容器
现有镜像的重新分配 - 将镜像从旧容器移动到新容器
数据库迁移 - 根据新容器更新镜像位置
1) 容器选择
此更改建议基于镜像 UUID 选择容器。镜像将存储在多个容器中,以避免在多个同时上传期间出现限制。镜像 UUID 的前 N 个字符,其中 N 是介于 1 和 32 之间的可配置整数,UUID 中十六进制数字的数量,默认值为 2,将用于确定镜像将上传到哪个容器。使用默认值的前两个字符,这将产生 16*16=256 个唯一的容器。在 N=1 时,这是此配置的最小有效值,将创建 16 个容器并用于存储镜像。容器的名称将根据 swift_store_container 设置的值,以及镜像 UUID 的前 N 个字符作为后缀来命名。
示例:如果将此配置选项设置为 3 并且 swift_store_container = ‘glance’,那么 UUID 为 ‘fdae39a1-bac5-4238-aba4-69bcc726e848’ 的镜像将被放置在 ‘glance_fda’ 容器中。UUID 中的所有破折号都包含在创建容器名称时,但不计入字符限制,因此在本例中,如果 N=10,容器名称将为 ‘glance_fdae39a1-ba’。
可以通过更改配置中的 N 来轻松增加或减少容器数量。但是,每次更改此配置时都会创建一组新的容器。在配置更改后创建的镜像将进入新容器,而旧镜像保留在其先前的容器中。旧镜像不一定需要移动到新容器,因为它们的位置仍然指向它们存储的现有旧容器。这意味着更改配置中的 N 不会删除现有的容器。但是,如果希望将旧镜像移动到新容器,可以通过重新分配镜像来执行此操作,这将在本节的后面进行描述。
注意:‘存储’镜像到容器意味着将清单和所有镜像分段存储在同一个容器中。除非另有说明,否则在整个规范中都将继续保持此情况。
2) 容器创建
Glance 附带一个配置选项,可以在将镜像数据上传到 Swift 时动态创建容器(如果它不存在)。这由配置选项 swift_store_create_container_on_put 指示。如果启用了动态容器创建,Glance 将在找不到适当的镜像容器时自动创建每个容器。
但是,如果禁用了动态容器创建的配置选项,如果部署者未手动创建适当的容器,则镜像上传将失败。如果未启用创建容器的配置选项,这种行为与 Glance 当前处理缺失容器的方式一致。
3) 现有镜像的重新分配(超出范围)
此规范不会提供代码或脚本来迁移现有镜像,因为延迟加载是分配新镜像的现有有效方法。但是,如果想迁移镜像,过程如下:一旦启用多个容器的使用或更改了容器数量,所有先前创建的镜像将保留在旧容器中。如果需要,可以将旧镜像移动到新容器中。这可以作为单独的批处理作业来完成,可以在需要时运行。根据旧镜像的数量,重新分配镜像可能涉及 Swift 集群中大量数据的移动。因此,分阶段且不具侵入性地实现这一点将很有帮助。重新分配镜像后,还需要更新它们的镜像位置。
4) 数据库迁移(超出范围)
如果镜像由操作员选择重新分配,则必须更新每个重新分配的镜像的镜像位置,以反映新的容器名称。这需要进行数据库迁移,以将位置中的旧容器名称替换为根据镜像 ID 的新容器名称。此迁移可以与重新分配同时进行。
此规范的范围
在上述四个方面中,此规范仅解决容器创建和选择,并将重新分配和所需的数据库迁移留给另一个协同工作来实施。
备选方案¶
1) 与使用镜像 ID 作为容器选择的基础相比,可以使用其他基础,例如租户 ID,这将使所有属于特定租户的镜像保存在同一个容器中。虽然其他容器名称基础是可能的,但使用镜像 ID 提供了一种更轻松地将镜像与其容器关联的方法。
2) 一种替代容器创建的方法是允许 API 在启动时创建所有必需的容器。这需要 API 在预先知道所有可能的容器,这取决于所选的容器选择基础,可能或不可能。这给人们可以选择的基础施加了一定的限制。因此,采用动态容器创建将消除此限制,因为容器选择和创建都可以是动态的。此外,动态容器创建与当前的 Glance 行为一致。
3) 与将多个镜像分组到一个容器中相比,另一种选择是为每个镜像提供自己的容器。但是,这不能解决任何问题,只是将基数问题从容器转移到帐户。此外,一些部署者限制了每个帐户允许的最大容器数量。白名单某些帐户以绕过容器限制将破坏 Swift 速率限制的目的,而这些速率限制是由部署者选择的,以保护整个集群。
数据模型影响¶
将创建并使用新的容器来存储镜像。但是,这不会对 Glance 镜像数据模型本身产生任何影响。
数据库迁移:
不需要数据库迁移。支持多个容器的代码只会影响新镜像的上传,确定它们属于哪个容器基于 UUID。对于现有镜像(在支持多个容器之前上传的镜像),镜像在其元数据中已经包含有效的位置。
REST API 影响¶
无
安全影响¶
鉴于此规范的范围,镜像数据未在新容器之间重新分配,并且未运行迁移,因此引入的安全影响微乎其微。
通知影响¶
此更改只会影响镜像属性中的镜像位置属性。并且,由于镜像位置不包含在通知中,因此不应对 Glance 通知产生任何影响。
其他最终用户影响¶
由于镜像位置对最终用户或来自 Glance 客户端不可见,因此不应对最终用户产生任何影响。
性能影响¶
使用多个容器将减少在同时上传多个镜像时的限制。这提高了大型部署中镜像创建和删除操作的并发性。
容器选择将发生在每次镜像上传请求时,从而为当前上传镜像数据的一组操作增加一个额外的操作。但是,选择容器将是一个简单的子字符串操作,用于获取镜像 ID 的前几个字符。确定容器所花费的时间将明显小于上传镜像数据所花费的时间。总体而言,容器选择的性能影响应该非常小。
容器创建是一个有条件的操作,只有当容器尚未存在时才会发生。这将为配置中指定的 N 个字符的每个组合发生一次。例如,默认配置选项是使用镜像 UUID 的前两个字符来选择适当的容器,从而产生总共 256 个容器,这对于中型部署来说应该是最佳的。我们发现,在大型部署中,如果选择了较小的分段大小,则 4096 个容器优于 256 个容器。创建新容器所花费的时间明显小于上传镜像数据所花费的时间。因此,镜像上传的整体性能影响应该很小。
其他部署者影响¶
此更改将在配置中启用多个容器后生效。启用后,新镜像将被上传到新容器,而现有镜像将保留在其先前分配的容器中。此更改是向前和向后兼容的,以便部署者可以随时选择启用或禁用多个容器,并且镜像仍然可以正确上传和下载。
部署者应注意,如果他们的部署限制了每个帐户的总容器数量,则应设置总容器数量的种子,以避免达到此限制。
glance-api.conf 中的新配置选项
swift_store_multiple_containers_seed - 默认 = 0
设置为 0 时,单租户存储只会使用一个容器来存储所有镜像。当设置为 1 到 32 之间的整数值时,单租户存储将使用多个容器来存储镜像,并且此值将确定创建多少个容器。仅在禁用 swift_store_multi_tenant 时使用。将使用的总容器数量大约等于 16^N,因此如果将此配置选项设置为 2,则将使用 16^2=256 个容器来存储镜像。
示例:如果将此配置选项设置为 3 并且 swift_store_container = ‘glance’,那么 UUID 为 ‘fdae39a1-bac5-4238-aba4-69bcc726e848’ 的镜像将被放置在 ‘glance_fda’ 容器中。UUID 中的所有破折号都包含在创建容器名称时,但不计入字符限制,因此在本例中,如果 N=10,容器名称将为 ‘glance_fdae39a1-ba’。
在选择 swift_store_multiple_containers_seed 的值时,部署者应与他们的 Swift 操作团队讨论合适的数值。此规范的作者建议大型部署使用值 ‘2’,这将创建最多约 256 个容器。即使在极大型部署中,选择高于此值的数值也可能不会对性能产生任何积极影响,并且可能导致大量空闲未使用的容器。如果关闭了动态容器创建,则此配置选项高于 ‘1’ 的任何值可能是不合理的,因为部署者将必须手动创建每个容器。
任何假设镜像存储在单个容器中的诊断/监控脚本可能需要进行适当的更改。
开发人员影响¶
无
实现¶
负责人¶
- 主要负责人
hemanth-makkapati
- 其他贡献者
ben-roble
评审人员¶
- 核心评审人
nikhil-komawar brian-rosmaita
- 其他审核员
无
工作项¶
在 Swift 存储驱动程序中实施新的配置选项
在 Swift 存储驱动程序中实施容器选择
实施单元、功能和集成测试
更改 glance 仓库中的 glance-api 示例配置文件
注意事项
所有代码更改将仅限于 glance_store 模块。
镜像下载代码不需要任何更改。
清单和分段都将进入同一个容器。
依赖项¶
无
测试¶
不需要 tempest 测试
文档影响¶
记录新的配置选项
参考资料¶
[1] https://docs.openstack.org/developer/swift/ratelimit.html#configuration