vm:01-clone-vm

Автоматизация клонирования Ubuntu Server VM в Hyper-V

Система позволяет создавать копии виртуальных машин Ubuntu Server за 2-3 минуты одним кликом. После клонирования SSH работает сразу, не требуется ручная настройка ключей или перезагрузка.

PowerShell скрипт выполняет:

  • Проверку существования эталонного образа
  • Создание структуры папок для новой VM
  • Копирование VHDX диска
  • Создание и настройку виртуальной машины
  • Автоматический запуск VM

При первой загрузке клона автоматически:

  • Создаётся папка /run/sshd (требуется для SSH)
  • Генерируются уникальные SSH host keys
  • Генерируется новый machine-id
  • SSH сервис запускается автоматически

Создайте файл New-VM.bat:

@echo off
PowerShell.exe -ExecutionPolicy Bypass -Command "Start-Process PowerShell -ArgumentList '-ExecutionPolicy Bypass -File \"%~dp0New-VMClone.ps1\"' -Verb RunAs"

Назначение: Запускает PowerShell скрипт с правами администратора одним двойным кликом.

Создайте файл New-VMClone.ps1 с кодировкой UTF-8 with BOM:

# Установка кодировки UTF-8
[Console]::OutputEncoding = [System.Text.Encoding]::UTF8
$OutputEncoding = [System.Text.Encoding]::UTF8
 
# Параметры
$TemplateVHD = "E:\template-vm\ubuntu-srv-template.vhdx"
$VMRootPath = "D:\Hyper-V"
$SwitchName = "external"
 
# Проверка что эталон существует
if (-not (Test-Path $TemplateVHD)) {
    Write-Host "ОШИБКА: Эталонный диск не найден: $TemplateVHD" -ForegroundColor Red
    Write-Host ""
    Read-Host "Нажмите Enter для выхода"
    exit
}
 
# Запрос параметров новой VM
Write-Host "=== Клонирование Ubuntu Server VM ===" -ForegroundColor Green
Write-Host ""
 
$VMName = Read-Host "Введите имя новой VM"
if ([string]::IsNullOrWhiteSpace($VMName)) {
    Write-Host "ОШИБКА: Имя VM не может быть пустым!" -ForegroundColor Red
    Write-Host ""
    Read-Host "Нажмите Enter для выхода"
    exit
}
 
# Проверка что VM с таким именем не существует
if (Get-VM -Name $VMName -ErrorAction SilentlyContinue) {
    Write-Host "ОШИБКА: VM с именем '$VMName' уже существует!" -ForegroundColor Red
    Write-Host ""
    Read-Host "Нажмите Enter для выхода"
    exit
}
 
$CPUCount = Read-Host "Количество процессоров (штук)"
if ([string]::IsNullOrWhiteSpace($CPUCount) -or $CPUCount -lt 1) {
    Write-Host "ОШИБКА: Укажите корректное количество процессоров!" -ForegroundColor Red
    Write-Host ""
    Read-Host "Нажмите Enter для выхода"
    exit
}
 
$RAMinGB = Read-Host "Объём памяти (GB)"
if ([string]::IsNullOrWhiteSpace($RAMinGB) -or $RAMinGB -lt 1) {
    Write-Host "ОШИБКА: Укажите корректный объём памяти!" -ForegroundColor Red
    Write-Host ""
    Read-Host "Нажмите Enter для выхода"
    exit
}
 
# Конвертируем GB в байты
$RAMBytes = [long]$RAMinGB * 1GB
 
Write-Host ""
Write-Host "=== Параметры новой VM ===" -ForegroundColor Cyan
Write-Host "Имя: $VMName"
Write-Host "CPU: $CPUCount"
Write-Host "RAM: $RAMinGB GB"
Write-Host ""
$Confirm = Read-Host "Создать VM? (y/n)"
if ($Confirm -ne "y") {
    Write-Host "Отменено." -ForegroundColor Yellow
    Write-Host ""
    Read-Host "Нажмите Enter для выхода"
    exit
}
 
# Создание папки для новой VM и подкаталога для дисков
$NewVMPath = Join-Path $VMRootPath $VMName
$VHDPath = Join-Path $NewVMPath "Virtual Hard Disks"
Write-Host ""
Write-Host "Создание папки: $NewVMPath" -ForegroundColor Yellow
New-Item -ItemType Directory -Path $NewVMPath -Force | Out-Null
New-Item -ItemType Directory -Path $VHDPath -Force | Out-Null
 
# Копирование VHDX
$NewVHDPath = Join-Path $VHDPath "$VMName.vhdx"
Write-Host "Копирование диска..." -ForegroundColor Yellow
Write-Host "Из: $TemplateVHD"
Write-Host "В: $NewVHDPath"
Copy-Item -Path $TemplateVHD -Destination $NewVHDPath -Force
 
# Создание VM
Write-Host "Создание виртуальной машины..." -ForegroundColor Yellow
New-VM -Name $VMName `
    -MemoryStartupBytes $RAMBytes `
    -Generation 2 `
    -VHDPath $NewVHDPath `
    -Path $VMRootPath `
    -SwitchName $SwitchName | Out-Null
 
# Настройка процессора
Set-VMProcessor -VMName $VMName -Count $CPUCount
 
# Отключение динамической памяти
Set-VMMemory -VMName $VMName -DynamicMemoryEnabled $false
 
# Настройка безопасной загрузки (для Linux)
Set-VMFirmware -VMName $VMName -EnableSecureBoot On -SecureBootTemplate MicrosoftUEFICertificateAuthority
 
# Запуск VM
Write-Host "Запуск виртуальной машины..." -ForegroundColor Yellow
Start-VM -Name $VMName
 
Write-Host ""
Write-Host "=== VM успешно создана и запущена! ===" -ForegroundColor Green
Write-Host "Имя VM: $VMName" -ForegroundColor Cyan
Write-Host "Путь: $NewVMPath" -ForegroundColor Cyan
Write-Host "Диск: $NewVHDPath" -ForegroundColor Cyan
Write-Host "CPU: $CPUCount процессоров" -ForegroundColor Cyan
Write-Host "RAM: $RAMinGB GB" -ForegroundColor Cyan
Write-Host ""
Write-Host "VM готова к работе!" -ForegroundColor Yellow
Write-Host "Подключение: ssh root@<IP-адрес>" -ForegroundColor Cyan
Write-Host "Пароль по умолчанию: 123456" -ForegroundColor Cyan
Write-Host ""
Write-Host "=== ВСЁ ГОТОВО! ===" -ForegroundColor Green
Write-Host ""
Read-Host "Нажмите Enter для выхода"

Параметры для настройки:

  • $TemplateVHD - путь к эталонному VHDX диску
  • $VMRootPath - корневая папка для виртуальных машин
  • $SwitchName - имя виртуального свитча Hyper-V

Установите Ubuntu Server 24.04 LTS и выполните начальную настройку:

# Обновление системы
apt update && apt upgrade -y
 
# Установка базовых утилит
apt install -y curl wget git htop nano net-tools
 
# Установка Docker
apt install -y docker.io docker-compose-v2
 
# Включение Docker в автозагрузку
systemctl enable docker
systemctl start docker
# Установка пароля для root (например: 123456)
passwd root
 
# Разрешение SSH входа для root
sed -i 's/#PermitRootLogin.*/PermitRootLogin yes/' /etc/ssh/sshd_config
sed -i 's/PermitRootLogin.*/PermitRootLogin yes/' /etc/ssh/sshd_config
 
# Перезапуск SSH
systemctl restart ssh
 
# Добавление root в группу docker
usermod -aG docker root

Теперь отключитесь и подключитесь под root, затем удалите стандартного пользователя:

# Удаление пользователя (замените username на реальное имя)
userdel -r username

Создайте скрипт автоматической регенерации SSH ключей:

cat > /usr/local/bin/regenerate-ssh-keys.sh << 'EOF'
#!/bin/bash
if [ ! -f /etc/ssh/ssh_host_rsa_key ]; then
    echo "Генерация SSH host keys..."
    ssh-keygen -A
    sleep 2
    pkill sshd
    sleep 1
    systemctl start ssh
    echo "SSH запущен"
fi
EOF
 
chmod +x /usr/local/bin/regenerate-ssh-keys.sh

Создайте systemd unit для автоматического запуска:

cat > /etc/systemd/system/regenerate-ssh-keys.service << 'EOF'
[Unit]
Description=Regenerate SSH host keys on first boot
Before=ssh.service
ConditionPathExists=!/etc/ssh/ssh_host_rsa_key
 
[Service]
Type=oneshot
ExecStart=/bin/bash -c 'ssh-keygen -A && sleep 2'
RemainAfterExit=yes
 
[Install]
WantedBy=multi-user.target
EOF
 
systemctl daemon-reload
systemctl enable regenerate-ssh-keys.service
# Создание tmpfiles конфигурации
cat > /etc/tmpfiles.d/sshd.conf << 'EOF'
d /run/sshd 0755 root root -
EOF
 
# Создание папки для текущей сессии
mkdir -p /run/sshd
chmod 0755 /run/sshd
# Включение SSH в автозагрузку
systemctl enable ssh
 
# Проверка статуса
systemctl status ssh

Убедитесь что SSH показывает: enabled и active (running)

Выполните финальную очистку и подготовку:

# Отключение и удаление swap файла
swapoff -a
rm -f /swap.img
sed -i '/swap.img/d' /etc/fstab
 
# Очистка APT кэша
apt clean
apt autoclean
 
# Удаление уникальных идентификаторов
rm -f /etc/machine-id
rm -f /var/lib/dbus/machine-id
touch /etc/machine-id
 
# Удаление SSH host keys (будут созданы автоматически)
rm -f /etc/ssh/ssh_host_*
 
# Очистка DHCP leases
rm -f /var/lib/dhcp/*
 
# Очистка логов
find /var/log -type f -exec truncate -s 0 {} \;
journalctl --vacuum-time=1s
 
# Очистка временных файлов
rm -rf /tmp/*
rm -rf /var/tmp/*
 
# Очистка истории команд
history -c
cat /dev/null > ~/.bash_history

Выключение VM:

shutdown -h now

<note important>ВАЖНО: После выключения НЕ запускайте эту VM! Это теперь эталонный образ для клонирования.</note>

На хосте Windows выполните в PowerShell от администратора:

# Сжатие VHDX
Optimize-VHD -Path "E:\template-vm\ubuntu-srv-template.vhdx" -Mode Full
 
# Проверка размера
Get-Item "E:\template-vm\ubuntu-srv-template.vhdx" | Select-Object Name, @{Name="Size(GB)";Expression={[math]::Round($_.Length/1GB,2)}}
 
# Создание резервной копии
Copy-Item "E:\template-vm\ubuntu-srv-template.vhdx" "E:\template-vm\ubuntu-srv-template-BACKUP.vhdx"
  1. Поместите файлы New-VM.bat и New-VMClone.ps1 в одну папку
  2. Убедитесь что пути в скрипте настроены правильно
  3. Запустите New-VM.bat двойным кликом
  4. Введите параметры новой VM
  5. Дождитесь завершения клонирования

Время создания VM: 2-3 минуты (зависит от размера диска)

SSH будет доступен сразу после загрузки клона!

E:\template-vm\
  └── ubuntu-srv-template.vhdx          # Эталонный образ

D:\Hyper-V\
  └── VMName\                            # Папка виртуальной машины
      ├── Virtual Machines\              # Конфигурация VM
      └── Virtual Hard Disks\            # Диски VM
          └── VMName.vhdx                # Клонированный диск

Подключитесь к консоли VM через Hyper-V Manager и проверьте:

# Проверка статуса SSH
systemctl status ssh
 
# Проверка SSH host keys
ls -l /etc/ssh/ssh_host_*
 
# Проверка сервиса регенерации
systemctl status regenerate-ssh-keys.service
 
# Узнать IP адрес
ip a

Ожидаемый результат:

  • ssh.service - active (running)
  • SSH host keys созданы (6-8 файлов)
  • regenerate-ssh-keys.service - показывает «Finished successfully»

После создания клона вы можете:

# Изменить hostname
hostnamectl set-hostname new-hostname
 
# Изменить пароль root
passwd root
 
# Перезагрузка
reboot

<note tip>Изменение hostname необязательно - система работает и с одинаковыми именами. Различать машины можно по IP адресам.</note>

# Проверка наличия папки /run/sshd
ls -ld /run/sshd
 
# Если папки нет - создайте вручную
mkdir -p /run/sshd
chmod 0755 /run/sshd
 
# Перезапуск SSH
systemctl restart ssh
# Ручная генерация ключей
ssh-keygen -A
 
# Перезапуск SSH
systemctl restart ssh
# Проверка на ошибки
sshd -t
 
# Просмотр логов
journalctl -u ssh -n 50

Теперь у вас есть полностью автоматизированная система клонирования Ubuntu Server VM. Каждый клон создаётся за 2-3 минуты с работающим SSH сразу после первой загрузки.

Преимущества:

  • Быстрое развертывание новых VM
  • Автоматическая генерация уникальных идентификаторов
  • SSH работает сразу без ручной настройки
  • Запуск одним кликом
  • Минимальный ручной труд
  • vm/01-clone-vm.txt
  • Последнее изменение: 2026/01/14 20:52
  • admin