Автоматизация задач администрирования API VMware vSphere с использованием Python

МЕНЮ


Искусственный интеллект
Поиск
Регистрация на сайте
Помощь проекту

ТЕМЫ


Новости ИИРазработка ИИВнедрение ИИРабота разума и сознаниеМодель мозгаРобототехника, БПЛАТрансгуманизмОбработка текстаТеория эволюцииДополненная реальностьЖелезоКиберугрозыНаучный мирИТ индустрияРазработка ПОТеория информацииМатематикаЦифровая экономика

Авторизация



RSS


RSS новости


2019-11-29 14:03

разработка по

В нашей компании активно используется платформа для виртуализации VMware vSphere. В ней живут тестовые среды продуктов, демонстрационные стенды, эмуляторы различных инфраструктур заказчиков и прочие не менее важные «виртуалки». Несмотря на достаточную мощность нашей инфраструктуры, доступ большого числа человек к управлению виртуальными машинами постоянно приводит к конфликтам и снижению производительности фермы. Разделение пулов между отделами (инженерами, тестировщиками, сейлами и разработчиками) проблему до конца не решает, поэтому периодически приходится разбираться, кто всем мешает и кто съел все ресурсы. При количестве виртуальных машин далеко за сотню сделать это вручную бывает проблематично, поэтому мы научились использовать API. VMware vSphere имеет довольно богатое API, которое незаслуженно слабо освещено на Хабре, хотя прикладная область применения довольна широка.
В данной статье будут приведены примеры взаимодействия в рамках задач администрирования с помощью Python.
Для Python есть библиотека под названием pyVmomi от самой VMware.


Подготовка

В папке проекта создадим конфигурационный файл config.txt следующего содержания:

[VSphere] host=10.10.1.2 user=admin@domain pwd=password

Для его чтения используем модуль configparser.

config = configparser.ConfigParser() config.read("config.txt")

Чтобы подключиться к сфере, используются методы pyVim.connect.SmartConnect и pyVim.connect.SmartConnectNoSSL. Второй применяется для самоподписанных сертификатов.

from pyVim.connect import SmartConnectNoSSL connection = SmartConnectNoSSL(**config["VSphere"])

Список машин по месту на датасторах

Предположим, на датасторах закончилось место. Эту проблему мы сейчас будем решать. Цель — получить список виртуальных машин, отсортированный по убыванию размера занятого места на датасторах. Также выведем максимальный размер файла, до которого может вырасти диск виртуальной машины, и количество места, занятого в гостевой системе.

Получить список виртуальных машин можно следующим образом:

from pyVmomi import vim  def get_all_vms():     content = connection.content     container = content.viewManager.CreateContainerView(content.rootFolder, [vim.VirtualMachine], True)     return [VirtualMachine(managed_object_ref) for managed_object_ref in container.view]

Как можно было заметить, возвращается список объектов класса VirtualMachine. Сейчас его и реализуем:

class VirtualMachine:     def __init__(self, machine_object):         self.vm = machine_object      @property     def name(self):         return self.vm.name      @property     def provisioned_space(self):         return int(self.vm.summary.storage.committed + self.vm.summary.storage.uncommitted) / 1024**3      @property     def guest_disk_usage(self):         return sum([int(i.capacity - i.freeSpace) for i in self.по размеру снапшотаvm.summary.vm.guest.disk]) / 1024**3      @property     def usage_storage(self):         return int(self.vm.summary.storage.committed) / 1024**3      def __repr__(self):         return "{}  {:.2f}  {:.2f}  {:.2f}".format(self.name, self.provisioned_space,                                                    self.guest_disk_usage, self.usage_storage)

Вывод данных уже зависит от необходимости. Самое простое — вывести в консоль:

for virtual_machine in sorted(get_all_vms(), key=lambda vm: vm.usage_storage, reverse=True):     print(virtual_machine)

Размеры и количество снапшотов

С размерами виртуальных машин разобрались. Предположим, мы хотим узнать, сколько снапшотов имеет каждая виртуальная машина, и сколько места они занимают.

Логика предыдущего примера сохраняется, только теперь наш класс VirtualMachine будет выглядеть так:

class VirtualMachine:     def __init__(self, machine_object):         self.vm = machine_object         self.snapshot_count, self.snapshot_size = self._snapshot_info()      @property     def name(self):         return self.vm.name      def _snapshot_info(self):         disk_list = self.vm.layoutEx.file         size = 0         count = 0         for disk in disk_list:             if disk.type == 'snapshotData':                 size += disk.size                 count += 1             ss_disk = re.search('0000dd', disk.name)             if ss_disk:                 size += disk.size         return count, size / 1024**3      def __repr__(self):         return "{}  {:.2f}  {}".format(self.name, self.snapshot_size, self.snapshot_count) 

И вывод будет отсортирован уже по размеру или по количеству:

for virtual_machine in sorted(get_all_vms(), key=lambda vm: vm.snapshot_size, reverse=True):     print(virtual_machine)

Восстановление снапшота

Раз пошла речь про снапшоты, то поговорим об их восстановлении.

Гипотетическая задача — восстановить последние созданные снапшоты, в названии которых присутствует строка infra.

Для восстановления снапшота необходимо создать задачу RevertToSnapshot_Task().

Сперва получим необходимый список машин:

def get_vms(part_of_name):     content = connection.content     container = content.viewManager.CreateContainerView(content.rootFolder, [vim.VirtualMachine], True)     return [managed_object_ref for managed_object_ref in container.view if part_of_name in managed_object_ref.name]

Для получения последнего созданного снапшота вернем последний элемент списка vm.snapshot.rootSnapshotList, отсортированного по полю createTime:

def get_last_snapshot(vm):     try:         return sorted(vm.snapshot.rootSnapshotList, key=lambda snap: snap.createTime)[-1]     except AttributeError:         return None

Теперь же можем восстановить этот снапшот:

def restore_snapshot(snaphot_obj):     task = snaphot_obj.snapshot.RevertToSnapshot_Task()     WaitForTask(task, connection)

Теперь все объединим:

part_of_name = "infra" for vm in get_vms(part_of_name):     last_snapshot = get_last_snapshot(vm)     if last_snapshot:         restore_snapshot(last_snapshot)

Включение/выключение по списку

Для выключения виртуальной машины необходимо создать задачу PowerOffVM_Task().

Напишем функцию выключения машины, если она включена:

def poweroff_if_enabled(vm):     if vm.runtime.powerState == vim.VirtualMachinePowerState.poweredOn:         vm.PowerOffVM_Task()

Итоговый скрипт:

part_of_name = "infra" for vm in get_vms(part_of_name):     poweroff_if_enabled(vm) 

Такое выключение машины будет принудительным. Гораздо правильнее будет вызвать задачу ShutdownGuest():

def shutdown_guest(vm):     if vm.runtime.powerState == vim.VirtualMachinePowerState.poweredOn:         vm.ShutdownGuest()

В конце хотелось бы привести еще несколько полезных ссылок:

  • pyvmomi samples — примеры от самой VMware
  • pyvmomi community samples — репозиторий с примерами использования библиотеки, написанными сообществом
  • govmomi — пакет для языка goland. Его использует kubernetes
  • rbvmomi — ruby-интерфейс для vSphere API

Если тема вызовет интерес, мы готовы ее продолжить и рассказать, как автоматизировать развертывание приложения от пуша в Git до создания виртуальной машины с работающим инстансом.

Источник: habr.com

Комментарии: