Proxmox. Часть 8. Создание виртуальной машины при помощи Terraform

В предыдущих частях заметок по Proxmox при необходимости создания виртуальной машины мы клонировали машину с шаблона. Существуют разные способы автоматизации этого процесса и один из них — Terraform.

Установка Terraform

Скачиваем бинарные файлы Terraform по ссылке https://developer.hashicorp.com/terraform/install в зависимости от вашей операционной системы:

Извлечем из архива бинарный файл terraform.exe. У меня получился такой путь до папки с terraform.exe: C:\Users\Nick\Downloads\terraform.

Если в консоли выполнить команду terraform, то получим ошибку:

«terraform» не является внутренней или внешней
командой, исполняемой программой или пакетным файлом.

или

‘terraform’ is not recognized as an internal or external command,
operable program or batch file.

Для решения этой проблемы откроем переменные среды Windows. Вы можете использовать поиск в панели задач (начните вводить «Переменных» и откройте пункт «Изменение системных переменных среды») или нажать клавиши Win+R на клавиатуре, ввести sysdm.cpl и нажать Enter.

Переменные среды:

В переменных выбираем Path и Изменить:

Создаем новую переменную и указываем путь до папки, где располагается terraform.exe:

Отжимаем во всех окнах Ok, проверяем в консоли:

Отлично, terraform установлен!

Настройка Proxmox и Terraform

Для автоматического создания виртуальных машин при помощи Terraform необходимо «подружить» Proxmox и Terraform. То есть сделать так, чтобы Proxmox понимал и принимал команды от Terraform. Воспользуемся инструкцией https://github.com/Telmate/terraform-provider-proxmox/blob/master/docs/index.md.

Первое, добавляем роль в Proxmox, используя которую Terraform будет общаться с Proxmox по API:

pveum role add TerraformProv -privs "Datastore.AllocateSpace Datastore.AllocateTemplate Datastore.Audit Pool.Allocate Sys.Audit Sys.Console Sys.Modify VM.Allocate VM.Audit VM.Clone VM.Config.CDROM VM.Config.Cloudinit VM.Config.CPU VM.Config.Disk VM.Config.HWType VM.Config.Memory VM.Config.Network VM.Config.Options VM.Migrate VM.Monitor VM.PowerMgmt SDN.Use"

Добавляем пользователя terraform-prov@pve c паролем nickcode:

pveum user add terraform-prov@pve --password nickcode

Присваиваем созданную роль созданному пользователю:

pveum aclmod / -user terraform-prov@pve -role TerraformProv

Проверим, что пользователь создан:

Залогинимся в Proxmox под созданным пользователем terraform-prov, пароль — nickcode:

И создадим Api token:

User — terraform@pve, Token ID — terraform, убираем галочку с Privilege Separation:

По нажатию на Add будет сгенерирован Token ID и Secret:

Cоздадим папку, в папке файл main.tf, в котором описываем параметры и количество создаваемых виртуальных машин. Там же описываем и параметры подключения к Proxmox, куда и вставим Токен и секрет:

terraform {
  required_providers {
    proxmox = {
      source = "Telmate/proxmox"
      version = "3.0.1-rc6"
    }
  }
}

provider "proxmox" {
  pm_tls_insecure = true
  pm_api_url = "https://192.168.31.23:8006/api2/json"
  # pm_user = "terraform@pve"
  pm_api_token_id = "terraform-prov@pve!terraform"
  pm_api_token_secret = "52383669-8b3c-4e76-beb1-e4ac1c4100b7"
  # pm_password = "123456#Terraform"
  pm_debug = true
}

# resource "random_password" "complex" {
#   count            = 42
#   length           = 20
#   min_upper        = 3
#   min_lower        = 3
#   min_numeric      = 3
# }

resource "proxmox_vm_qemu" "virt" {
  count = 1
  name = "virt-${count.index + 1}"
  vmid = "${count.index+1165}"
  target_node = "${var.proxmox_host}"
  clone = "${var.template_name}"
  define_connection_info = true
  agent = 1
  os_type = "cloud-init"
  cores = 1
  sockets = 1
  cpu_type = "host"
  memory = 2048
  sshkeys = "${var.ssh_keys}"
  scsihw = "virtio-scsi-pci"
  #bootdisk = "scsi0"
  ciuser = "ubuntu"
  cipassword = "nickcode"
  ipconfig0 = "ip=192.168.31.${count.index + 70}/24,gw=192.168.31.1"

  boot = "order=scsi0"

  serial {
        id   = 0
        type = "socket"
    }

  disks {
      ide {
          ide2 {
              cloudinit {
                  storage = "local-lvm"
              }
          }
      }
      scsi {
          scsi0 {
              disk {
                  size            = 20
                  storage         = "local-lvm"
              }
          }
      }
  }

  network {
    id = 0
    model = "virtio"
    bridge = "vmbr0"
  }
  # lifecycle {
  #   ignore_changes = [
  #     network,
  #   ]
  # }

  connection {
   type        = "ssh"
   user        = "ubuntu"
   private_key = file("./sshterraform")
   host        = self.ssh_host
   port        = self.ssh_port
  }

  provisioner "remote-exec" {
    inline = [
      "sudo apt update",
      "export DEBIAN_FRONTEND=noninteractive",
      "export NEEDRESTART_MODE=a",
      "sudo -E apt -y upgrade"
    ]
  }

}

В этой же папке создадим файл var.tf, в котором будут располагаться переменные, которые используем в main.tf. Вставим туда следующее:

variable "proxmox_host" {
    default = "pve"
}
variable "template_name" {
    default = "ubuntu2404"
}

variable "ssh_keys" {
    type = string 
    default = <<EOF
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABgQDowlg64xSfAhmdrwhEV4gVR6+ZjJgtSbvnLnFccOE/pDwvmnp9d9DiKHrl3vHqDwozUkgGRdqLBrBa3rT2ngnwKET0Ijotz76GTsjPYG/1PDrdAsnz+OOJnqp1llGEHewORWGirkWpHEM5GMV5vnXAsNqaZwziafoI1d2eaydpieB2tAeFXb5XdsrGF2xPV/sT7EDiJt7VyFWKBprkCkhzzPv12bPuz2xmqC2QeNKdLS3OG52ydAHEwfvMC5M226SloDxY5uYVNae4kM3dekVZ76R+xiRBzyFcMWgf6X//pH9lYhKFRFW1ebIDpFJbeztvfYfZTH6yUjAuyqS4m3TN4E/7biEYsL6wWr3fmNqQeax6/RABncXihzLY4DsEPM+vNA7awgiXNAUIeqAOuc9RqbPkUePwTGqTmRwn7H5OUqUDz2voQsAQbW/+4hhv1EDSIIWZPK8+KvQsCfgU/Y+tCtOH8SCYdCM5omCM5mAAFqxDKeKFeb0yR6hX+NgYFYE= nick@WIN-L7I5C6480VP
EOF
}

Откроем папку в консоли и попробуем выполнить инициализацию рабочего каталога Terraform:

terraform init

и с большой долей вероятности получаем ошибку:

Initializing the backend…

Initializing provider plugins…

— Reusing previous version of telmate/proxmox from the dependency lock file

Error: Invalid provider registry host

The host «registry.terraform.io» given in provider source address «registry.terraform.io/telmate/proxmox» does not offer a Terraform provider registry.

Если ошибку не получили, то можно пропустить следующие шаги до следующей инициализации (terraform init).

Для решения этой проблемы скачиваем бинарные файлы Proxmox provider.

Для этого переходим по ссылке https://github.com/Telmate/terraform-provider-proxmox/releases и скачиваем последнюю версию для вашей ОС:

В моем случае актуальная версия 3.0.1-rc6, скачиваю вариант для windows_arm64:

https://github.com/Telmate/terraform-provider-proxmox/releasesterraform-provider-proxmox_3.0.1-rc6_windows_amd64.zip

Создаем папку:

mkdir "%APPDATA%\terraform.d\plugins\registry.terraform.io\telmate\proxmox\3.0.1-rc6\windows_amd64\"

Перейдем в папку

%APPDATA%\terraform.d\plugins\registry.terraform.io\telmate\proxmox\3.0.1-rc6\windows_amd64\

И скопируем туда скачанный бинарный файл:

terraform-provider-proxmox_v3.0.1-rc6.exe

Убедимся, что в конфигурационном файле terraform main.tf версия такая же, как мы скачали:

В папке с проектом ищем и удаляем файл terraform.lock.hcl и еще раз пробуем инициализировать рабочий каталог Terraform:

terraform init

Терраформ успешно инициализирован!

Для доступа к созданным виртуальным машинам сгенерируем SSH ключи

ssh-keygen -t rsa

Скопируем публичный ключ sshterraform.pub и поместим в var.tf:

Приватный ключ sshterraform поместим в папку вместе с конфигурационным файлом main.tf.

В main.tf настроим подключение по ssh к создаваемой машине:

Клонирование виртуальной машины при помощи Terraform

Вернемся в Proxmox и переименуем наш шаблон виртуальной машины с VM 9000 на ubuntu2404:

В консоли, где мы инициализировали терраформ, проверим main.tf на корректность:

terraform validate

Сгенерируем файл изменений:

terraform plan

Для применения изменений, которые мы описали в main.tf, выполним:

terraform apply

Введем “yes”. Можно использовать флаг --auto-approve, для пропуска данного подтверждения.

Начинается процесс клонирования и настройки виртуальной машины:

В консоли Proxmox можно заметить, что клонирование идет от созданного нами пользователя:

После того, как виртуальная машина будет создана и доступна, terraform подключится по ssh и выполнит команды, которые мы указали в блоке «remote-exec«:

Виртуальная машина по нашему шаблону в конфигурационном файле main.tf успешно создана:

Для просмотра параметров созданной машины выполним команду:

terraform show

Удалим созданную виртуальную машину:

terraform destroy

Виртуальная машина удалена!