我正在 Azure 云中基于
instancesCount
变量使用 ansible 部署任意数量的实例,并使用 with_sequence: count={{ instancesCount }}
迭代每个资源(NIC、托管磁盘、VM 等)的创建任务。实例及其关联资源(托管磁盘、操作系统磁盘、NIC)以相同的名称格式创建:
{{ env }}-xxx-{{ vmName }}-{{ count }}:
say instancesCount is 3:
dev-xxx-myvm-1
dev-xxx-myvm-1-nic
dev-xxx-myvm--1-osDisk
dev-xxx-myvm-2
dev-xxx-myvm-2-nic
dev-xxx-myvm-2-osDisk
dev-xxx-myvm-3
dev-xxx-myvm-3-nic
dev-xxx-myvm-3-osDisk
我正在寻找一种方法,当变量
instancesCount
更改为较小的整数(例如从3到1)时,通过首先删除最新实例来减少实例数量:dev-xxx-myvm-3
,dev-xxx-myvm-2
,及其相关资源,只剩下 dev-xxx-myvm-1
。
我想到的逻辑是首先使用每个资源的 Ansible 模块从 Azure 收集信息(
azure_rm_virtualmachine_info
、azure_rm_networkinterface_info
、azure_rm_manageddisk_info
等)。将每个变量保存在自己的变量中,并使用它和instancesCount,删除超出的资源,但我不知道如何继续..
使用 jinja2 我可以轻松删除要删除的虚拟机名称,但无法将此代码转换为 Ansible:
{% set to_remove = existing_vms.vms | length - instancesCount | int %}
{% for item in existing_vms.vms[-to_remove:] %}
{{ item.name }}
{% endfor %}
能够成功转换:
- name: Print name of vms to be removed
debug:
var: item.name
loop: "{{ existing_vms.vms[-(to_remove|int):] }}"
然而,最后一个问题:列表未排序。假设我们有 10 个实例,
existing_vms.vms.*.name
看起来像这样,因为它是从 Azure 中提取的:
dev-xxx-myvm-1
dev-xxx-myvm-10
dev-xxx-myvm-2
dev-xxx-myvm-3
dev-xxx-myvm-4
dev-xxx-myvm-5
dev-xxx-myvm-6
dev-xxx-myvm-7
dev-xxx-myvm-8
dev-xxx-myvm-9
在将列表传递给切片运算符之前,我如何能够按名称中的尾随数字升序对列表进行排序 -
[-(to_remove)|int:]
?
正确的解决方案是使用
azure_rm_virtualmachine_info
查找已部署的虚拟机,将其保存在变量中并清理该变量,然后在指定 azure_rm_virtualmachine
时将其传递给 remove_on_absent
。无需获取托管磁盘、网卡或任何其他资源信息,因为这将删除依赖资源。
- name: "Getting deployment state"
block:
- name: "Getting deployment state"
azure.azcollection.azure_rm_virtualmachine_info:
resource_group: myRG
register: existing_vms
- name: Saving all VM names in vm_names
ansible.builtin.set_fact:
vm_names: "{{ vm_names | default([]) + [item.name] }}"
loop: "{{ existing_vms.vms }}"
- name: Sorting the VM names in vm_names_sorted
ansible.builtin.set_fact:
vm_names_sorted: "{{ vm_names | community.general.version_sort }}"
ignore_errors: true
这将正确排序列表:
来自:
dev-xxx-myvm-1
dev-xxx-myvm-10
dev-xxx-myvm-2
dev-xxx-myvm-3
dev-xxx-myvm-4
dev-xxx-myvm-5
dev-xxx-myvm-6
dev-xxx-myvm-7
dev-xxx-myvm-8
dev-xxx-myvm-9
致:
dev-xxx-myvm-1
dev-xxx-myvm-2
dev-xxx-myvm-3
dev-xxx-myvm-4
dev-xxx-myvm-5
dev-xxx-myvm-6
dev-xxx-myvm-7
dev-xxx-myvm-8
dev-xxx-myvm-9
dev-xxx-myvm-10
- name: "Setting scale down value if instancesCount < currrent deployment"
ansible.builtin.set_fact:
to_remove: "{{ vm_names_sorted | length - instancesCount | int }}"
when: vm_names_sorted is defined and vm_names_sorted | length | int > instancesCount | int and instancesCount | int != 0
azure_rm_virtualmachine
以删除 to_remove 数量的虚拟机,从最新的(dev-xxx-myvm-10、dev-xxx-myvm-9 等)开始:
- name: "Scaling down deployment to {{ instancesCount }}"
azure.azcollection.azure_rm_virtualmachine:
resource_group: myRG
name: "{{ item }}"
remove_on_absent: ['network_interfaces', 'virtual_storage', 'public_ips']
state: absent
loop: "{{ vm_names_sorted[-(to_remove|int):] }}"
when: to_remove is defined