master
Долгий Артём 2023-03-11 17:19:54 +03:00
commit 3f19cfc745
5 changed files with 317 additions and 0 deletions

1
.gitignore vendored Normal file
View File

@ -0,0 +1 @@
/venv/

92
blank_proxmoxer.py Executable file
View File

@ -0,0 +1,92 @@
from proxmoxer import ProxmoxAPI
import yaml
import os.path
import urllib.request
with open('vars.yaml') as data:
vars_dict = yaml.safe_load(data)
# параметры хоста Proxmox
proxmox_node = vars_dict['proxmox_node']['name']
pve_host = vars_dict['proxmox_node']['host']
pve_port = vars_dict['proxmox_node']['port']
pve_admin = vars_dict['proxmox_node']['username']
pve_passwd = vars_dict['proxmox_node']['password']
pve_storage = vars_dict['proxmox_node']['storage']
pve_net = vars_dict['proxmox_node']['net']
# параметры создаваемого шаблона
tmpl_id = vars_dict['template']['id']
tmpl_name = vars_dict['template']['name']
tmpl_cores = vars_dict['template']['cores']
tmpl_memory = vars_dict['template']['memory']
tmpl_user = vars_dict['template']['username']
tmpl_passwd = vars_dict['template']['password']
# ссылка на образ
img_url = vars_dict['img']['url']
img_name = vars_dict['img']['name']
def download_img(name, url):
"""
Проверка наличия образа в текущей директории.
Если образа нет, он скачивается.
Params:
name - (str), имя образа;
url - (str), url-ссылка на директорию с образом.
Return:
None
"""
if os.path.isfile(name):
print(f'Файл с именем "{name}" присутствует в текущей директории')
else:
print(f'Образа "{name}" нет в текущей директории, скачиваю..')
urllib.request.urlretrieve(f'{url}/{name}', name)
print('Скачивание завершено.')
def create_vm(node, **kwargs):
"""
Создание шаблона ВМ из ранее скачанного образа.
Params:
node - (class 'proxmoxer.core.ProxmoxResource'), хост Proxmox,
на котором создаётся шаблон.
Return:
None
"""
node.qemu.create(
vmid=tmpl_id, name=tmpl_name, cores=tmpl_cores, memory=tmpl_memory,
net0=f'virtio,bridge={pve_net}', bootdisk='scsi0',
ide0=f'{pve_storage}:cloudinit', ide2='none,media=cdrom', vga='qxl',
ciuser=tmpl_user, cipassword=tmpl_passwd, agent=1)
def importdisk(node, img, stor, **kwargs):
"""
Импорт образа в ВМ.
Params:
node - (class 'proxmoxer.core.ProxmoxResource'), хост Proxmox,
на котором создаётся шаблон.
Return:
None
"""
node.qemu.importdisk(img, stor)
proxmox = ProxmoxAPI(host=pve_host, user=pve_admin, password=pve_passwd, port=pve_port, verify_ssl=True)
pve_node = proxmox.nodes(proxmox_node)
# download_img(name=img_name, url=img_url)
# create_vm(node=pve_node)
# importdisk(node=pve_node, img=img_name, stor=pve_storage)
pve_node.qemu(f'disk import {tmpl_id} {img_name} {pve_storage},format=qcow2')

70
deploy_aldpro_vm.py Executable file
View File

@ -0,0 +1,70 @@
#!/usr/bin/env python3
import subprocess
from pprint import pprint
import yaml
with open('vars.yaml') as data:
vars_dict = yaml.safe_load(data)
def shell_run(cmd):
"""
Выполнение shell команды.
:param cmd: (str), команда.
:return: proc.stdout: (subprocess object), вывод команды
proc.stderr: (subprocess object), код завершения.
"""
proc = subprocess.run(
cmd.split(), capture_output=True, text=True, timeout=60)
if proc.stderr:
print(f'Команда - "{cmd}"')
print(proc.stderr)
exit(1)
return proc.stdout, proc.stderr
def gen_vm_commands(all_dict):
"""
Генерация списка команд для создания группировки ВМ ALD Pro.
:param all_dict: (dict), словарь с переменными для генерации.
:return: (dict), словарь списков команд.
"""
tmpl_id = all_dict['template']['id']
gw = all_dict['proxmox_node']['vmbr_gw']
commands = {}
for vm in vars_dict['vms']:
vm_cmds = [f'qm clone {tmpl_id} {vm["id"]} --name {vm["name"]} --full',
f'qm set {vm["id"]} --ipconfig0 ip={vm["ip"]}/24,gw={gw}',
f'qm resize {vm["id"]} scsi0 32G']
if vm["name"] == 'dc01' or vm["name"] == 'dc02':
vm_cmds.append(f'qm set {vm["id"]} --cores 4 --memory 8192')
vm_cmds.remove(f'qm resize {vm["id"]} scsi0 32G')
vm_cmds.append(f'qm resize {vm["id"]} scsi0 64G')
elif vm["name"] == 'repo':
vm_cmds.remove(f'qm resize {vm["id"]} scsi0 32G')
vm_cmds.append(f'qm resize {vm["id"]} scsi0 64G')
commands.update({vm["name"]: vm_cmds})
return commands
def create_vms(commands_dict):
"""
Создание группировки ВМ ALD Pro.
:param commands_dict: (dict), словарь списков команд для создания ВМ.
:return: None
"""
for role in commands_dict.items():
print(f'Создаётся ВМ - {role[0]}')
for cmd in role[1]:
shell_run(cmd)
if __name__ == "__main__":
cmds = gen_vm_commands(vars_dict)
create_vms(cmds)
# pprint(cmds)

105
deploy_template_subprocess.py Executable file
View File

@ -0,0 +1,105 @@
#!/usr/bin/env python3
import subprocess
import yaml
from pathlib import Path
import urllib.request
with open('vars.yaml') as data:
vars_dict = yaml.safe_load(data)
# параметры хоста Proxmox
proxmox_node = vars_dict['proxmox_node']['name']
pve_host = vars_dict['proxmox_node']['host']
pve_port = vars_dict['proxmox_node']['port']
pve_admin = vars_dict['proxmox_node']['username']
pve_passwd = vars_dict['proxmox_node']['password']
pve_storage = vars_dict['proxmox_node']['storage']
pve_vmbr = vars_dict['proxmox_node']['vmbr']
# параметры создаваемого шаблона
tmpl_id = vars_dict['template']['id']
tmpl_name = vars_dict['template']['name']
tmpl_cores = vars_dict['template']['cores']
tmpl_memory = vars_dict['template']['memory']
tmpl_user = vars_dict['template']['username']
tmpl_passwd = vars_dict['template']['password']
# ссылка на образ
img_url = vars_dict['img']['url']
img_name = vars_dict['img']['name']
def download_img(name, url):
"""
Проверка наличия образа в текущей директории.
Если образа нет, он скачивается.
:param name: (str), имя образа;
:param url: (str), url-ссылка на директорию с образом.
:return: None.
"""
if Path(name).is_file():
print(f'Файл с именем "{name}" присутствует в текущей директории')
else:
print(f'Образа "{name}" нет в текущей директории, скачиваю..')
urllib.request.urlretrieve(f'{url}/{name}', name)
print('Скачивание завершено.')
def del_img(name):
"""
Удаление образа из текущей директории.
:param name: (str), имя образа.
:return: None
"""
if Path(name).is_file():
proc = subprocess.run(f'rm -rf {name}'.split(), capture_output=True, text=True)
print(f'Образ "{name}" удалён из текущей директории')
if proc.stderr:
print(f'Команда - "rm -rf {name}"')
print(proc.stderr)
exit(1)
else:
print(f'Образа "{name}" нет в текущей директории, скачиваю..')
def deploy_template(list_commands):
"""
Функция поочерёдно выполняет shell команды, переданные списком.
:param list_commands: (list), список команд, которые необходимо выполнить.
:return: None
"""
print(f'Создаю шаблон ВМ из образа')
for com in list_commands:
proc = subprocess.run(com.split(), capture_output=True, text=True)
if proc.stderr:
print(f'Команда - "{com}"')
print(proc.stderr)
exit(1)
# else:
# print(proc.stdout)
print('Шаблон создан.')
if __name__ == "__main__":
# в зависимости от типа и нахождения хранилища
# путь к создаваемому в процессе импорта диску указывается по-разному
# см. в WEB-интерфейсе примеры с других ВМ
commands = [f'qm create {tmpl_id} --name {tmpl_name}',
f'qm set {tmpl_id} --memory {tmpl_memory} --cores {tmpl_cores}',
f'qm set {tmpl_id} --net0 virtio,bridge={pve_vmbr} --scsihw virtio-scsi-pci',
f'qm disk import {tmpl_id} {img_name} {pve_storage} --format qcow2',
f'qm set {tmpl_id} --scsi0 {pve_storage}:{tmpl_id}/vm-{tmpl_id}-disk-0.qcow2',
f'qm set {tmpl_id} --bootdisk scsi0',
f'qm set {tmpl_id} --ide0 {pve_storage}:cloudinit --ide2 none,media=cdrom',
f'qm set {tmpl_id} --vga qxl --agent 1',
f'qm set {tmpl_id} --ciuser={tmpl_user} --cipassword={tmpl_passwd}',
f'qm template {tmpl_id}']
download_img(img_name, img_url)
deploy_template(commands)
del_img(img_name)

49
vars.yaml Normal file
View File

@ -0,0 +1,49 @@
---
proxmox_node:
name: pve
ip: 192.168.13.19
host: pve.da2001.ru
port: 443
username: root@pam
password: KatIrina1
storage: testvms
vmbr: vmbr1
vmbr_gw: 10.1.1.9
template:
name: alse-1703-cloudinit-template
id: 400
cores: 2
memory: 2048
username: sysadmin
password: KatIrina1
img:
name: alse-vanilla-1.7.3-cloud-max-mg9.1.2.qcow2
url: https://vault.astralinux.ru/images/alse/cloud
vms:
- name: dc01
id: 401
ip: 10.1.1.11
- name: dc02
id: 402
ip: 10.1.1.12
- name: repo
id: 403
ip: 10.1.1.13
- name: dhcp
id: 404
ip: 10.1.1.14
- name: pxe
id: 405
ip: 10.1.1.15
- name: nas
id: 406
ip: 10.1.1.16
- name: monitoring
id: 407
ip: 10.1.1.17
- name: printserver
id: 408
ip: 10.1.1.18