孤立资源分配¶
问题¶
在 Placement 服务中存在孤立资源分配,这可能导致资源提供者
向调度器显示比实际更多的利用率
阻止删除计算服务
一种可能发生这种情况的场景是,计算服务主机遇到问题,管理员强制其下线并从其上撤离服务器。请注意,在这种情况下,“撤离”指的是服务器 evacuate 操作,而不是从正在运行的计算服务中实时迁移所有服务器。假设计算主机已下线并已隔离。
在这种情况下,服务器的分配在 Placement 中针对已下线的源计算节点和其当前目标计算主机进行跟踪。例如,这里有一个服务器 vm1,它已从节点 devstack1 撤离到节点 devstack2
$ openstack --os-compute-api-version 2.53 compute service list --service nova-compute
+--------------------------------------+--------------+-----------+------+---------+-------+----------------------------+
| ID | Binary | Host | Zone | Status | State | Updated At |
+--------------------------------------+--------------+-----------+------+---------+-------+----------------------------+
| e3c18c2d-9488-4863-b728-f3f292ec5da8 | nova-compute | devstack1 | nova | enabled | down | 2019-10-25T20:13:51.000000 |
| 50a20add-cc49-46bd-af96-9bb4e9247398 | nova-compute | devstack2 | nova | enabled | up | 2019-10-25T20:13:52.000000 |
| b92afb2e-cd00-4074-803e-fff9aa379c2f | nova-compute | devstack3 | nova | enabled | up | 2019-10-25T20:13:53.000000 |
+--------------------------------------+--------------+-----------+------+---------+-------+----------------------------+
$ vm1=$(openstack server show vm1 -f value -c id)
$ openstack server show $vm1 -f value -c OS-EXT-SRV-ATTR:host
devstack2
现在,服务器在 Placement 服务中的 devstack1 和 devstack2 资源提供者上都有分配
$ devstack1=$(openstack resource provider list --name devstack1 -f value -c uuid)
$ devstack2=$(openstack resource provider list --name devstack2 -f value -c uuid)
$ openstack resource provider show --allocations $devstack1
+-------------+-----------------------------------------------------------------------------------------------------------+
| Field | Value |
+-------------+-----------------------------------------------------------------------------------------------------------+
| uuid | 9546fce4-9fb5-4b35-b277-72ff125ad787 |
| name | devstack1 |
| generation | 6 |
| allocations | {u'a1e6e0b2-9028-4166-b79b-c177ff70fbb7': {u'resources': {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1}}} |
+-------------+-----------------------------------------------------------------------------------------------------------+
$ openstack resource provider show --allocations $devstack2
+-------------+-----------------------------------------------------------------------------------------------------------+
| Field | Value |
+-------------+-----------------------------------------------------------------------------------------------------------+
| uuid | 52d0182d-d466-4210-8f0d-29466bb54feb |
| name | devstack2 |
| generation | 3 |
| allocations | {u'a1e6e0b2-9028-4166-b79b-c177ff70fbb7': {u'resources': {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1}}} |
+-------------+-----------------------------------------------------------------------------------------------------------+
$ openstack --os-placement-api-version 1.12 resource provider allocation show $vm1
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
| resource_provider | generation | resources | project_id | user_id |
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
| 9546fce4-9fb5-4b35-b277-72ff125ad787 | 6 | {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1} | 2f3bffc5db2b47deb40808a4ed2d7c7a | 2206168427c54d92ae2b2572bb0da9af |
| 52d0182d-d466-4210-8f0d-29466bb54feb | 3 | {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1} | 2f3bffc5db2b47deb40808a4ed2d7c7a | 2206168427c54d92ae2b2572bb0da9af |
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
一种查找所有从 devstack1 撤离的服务器的方法是
$ nova migration-list --source-compute devstack1 --migration-type evacuation
+----+--------------------------------------+-------------+-----------+----------------+--------------+-------------+--------+--------------------------------------+------------+------------+----------------------------+----------------------------+------------+
| Id | UUID | Source Node | Dest Node | Source Compute | Dest Compute | Dest Host | Status | Instance UUID | Old Flavor | New Flavor | Created At | Updated At | Type |
+----+--------------------------------------+-------------+-----------+----------------+--------------+-------------+--------+--------------------------------------+------------+------------+----------------------------+----------------------------+------------+
| 1 | 8a823ba3-e2e9-4f17-bac5-88ceea496b99 | devstack1 | devstack2 | devstack1 | devstack2 | 192.168.0.1 | done | a1e6e0b2-9028-4166-b79b-c177ff70fbb7 | None | None | 2019-10-25T17:46:35.000000 | 2019-10-25T17:46:37.000000 | evacuation |
+----+--------------------------------------+-------------+-----------+----------------+--------------+-------------+--------+--------------------------------------+------------+------------+----------------------------+----------------------------+------------+
尝试删除 devstack1 的资源提供者将在其上存在分配时失败
$ openstack resource provider delete $devstack1
Unable to delete resource provider 9546fce4-9fb5-4b35-b277-72ff125ad787: Resource provider has allocations. (HTTP 409)
解决方案¶
使用上面的示例资源,从 devstack1 资源提供者中删除服务器 vm1 的分配。如果您拥有 osc-placement 1.8.0 或更高版本,可以使用 openstack resource provider allocation unset 命令从资源提供者 devstack1 中删除消费者 vm1 的分配
$ openstack --os-placement-api-version 1.12 resource provider allocation \
unset --provider $devstack1 $vm1
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
| resource_provider | generation | resources | project_id | user_id |
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
| 52d0182d-d466-4210-8f0d-29466bb54feb | 4 | {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1} | 2f3bffc5db2b47deb40808a4ed2d7c7a | 2206168427c54d92ae2b2572bb0da9af |
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
如果您拥有 osc-placement 1.7.x 或更早版本,则 unset 命令不可用,您必须改用覆盖分配。请注意,我们这里不使用 openstack resource provider allocation delete,因为这将从所有资源提供者(包括 devstack2,服务器现在正在运行的地方)删除服务器的分配;相反,我们使用 openstack resource provider allocation set 来覆盖分配并仅保留 devstack2 提供者的分配。如果您删除了给定服务器的所有分配,稍后可以修复它们。有关详细信息,请参阅 使用 heal_allocations。
$ openstack --os-placement-api-version 1.12 resource provider allocation set $vm1 \
--project-id 2f3bffc5db2b47deb40808a4ed2d7c7a \
--user-id 2206168427c54d92ae2b2572bb0da9af \
--allocation rp=52d0182d-d466-4210-8f0d-29466bb54feb,VCPU=1 \
--allocation rp=52d0182d-d466-4210-8f0d-29466bb54feb,MEMORY_MB=512 \
--allocation rp=52d0182d-d466-4210-8f0d-29466bb54feb,DISK_GB=1
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
| resource_provider | generation | resources | project_id | user_id |
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
| 52d0182d-d466-4210-8f0d-29466bb54feb | 4 | {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1} | 2f3bffc5db2b47deb40808a4ed2d7c7a | 2206168427c54d92ae2b2572bb0da9af |
+--------------------------------------+------------+------------------------------------------------+----------------------------------+----------------------------------+
一旦使用上述任何一种方法删除了 devstack1 资源提供者的分配,就可以删除 devstack1 资源提供者
$ openstack resource provider delete $devstack1
以及相关的计算服务(如果需要)
$ openstack --os-compute-api-version 2.53 compute service delete e3c18c2d-9488-4863-b728-f3f292ec5da8
有关本指南中使用的资源提供者命令的更多详细信息,请参阅 osc-placement 插件文档。
使用 heal_allocations¶
如果您有一个特别棘手的分配消费者,只想从所有提供者中删除其分配,可以使用 openstack resource provider allocation delete 命令,然后使用 heal_allocations 命令 修复消费者的分配。例如
$ openstack resource provider allocation delete $vm1
$ nova-manage placement heal_allocations --verbose --instance $vm1
Looking for instances in cell: 04879596-d893-401c-b2a6-3d3aa096089d(cell1)
Found 1 candidate instances.
Successfully created allocations for instance a1e6e0b2-9028-4166-b79b-c177ff70fbb7.
Processed 1 instances.
$ openstack resource provider allocation show $vm1
+--------------------------------------+------------+------------------------------------------------+
| resource_provider | generation | resources |
+--------------------------------------+------------+------------------------------------------------+
| 52d0182d-d466-4210-8f0d-29466bb54feb | 5 | {u'VCPU': 1, u'MEMORY_MB': 512, u'DISK_GB': 1} |
+--------------------------------------+------------+------------------------------------------------+
请注意,删除分配然后依赖 heal_allocations 可能并非总是最佳解决方案,因为修复分配并不能考虑某些事项
基于迁移的分配如果在调整大小期间手动删除,将会丢失。这些是在迁移期间在源计算服务上跟踪的迁移资源记录的分配。
修复分配仅部分支持嵌套分配。从 20.0.0 (Train) 版本开始,由于 Neutron 端口具有 QoS 策略而导致的嵌套分配受支持。但是,由于 flavor 中 vGPU 或 Cyborg 设备配置文件请求而导致的嵌套分配不受支持。此外,如果您在计算主机上使用 provider.yaml 文件来定义其他资源,如果这些资源在子资源提供者上定义,则使用这些资源的实例不受支持。
如果您使用 heal_allocations 命令清理特定麻烦实例的分配,建议记录分配在删除它们之前是什么,以防以后需要手动重置它们。使用 openstack resource provider allocation show 命令在删除它们之前获取消费者的分配,例如:
$ openstack --os-placement-api-version 1.12 resource provider allocation show $vm1
使用 Placement 审计¶
如果您遇到过去已删除的实例存在孤立分配的情况,例如日志消息
Instance <uuid> has allocations against this compute host but is not found in the database.
您可以使用 nova-manage placement audit 工具来查找并选择性地删除孤立的 Placement 分配。此工具将调用 Placement API 来修改分配。
要列出与现有实例或迁移 UUID 无关的所有分配
$ nova-manage placement audit --verbose
要删除所有资源提供者上与现有实例或迁移 UUID 无关的所有分配
$ nova-manage placement audit --verbose --delete
要删除特定资源提供者上与现有实例或迁移 UUID 无关的所有分配
$ nova-manage placement audit --verbose --delete --resource-provider <uuid>