Reorganize the brownfield repository, remove retired and generated artifacts, harden ignore rules, and record the GitOps/IaC redesign.
106 lines
4.0 KiB
YAML
106 lines
4.0 KiB
YAML
---
|
|
# Create + unattended-install a Windows Server 2025 admin box on local libvirt.
|
|
# Runs on localhost (qemu:///system, become: true). Idempotent on the domain existing.
|
|
|
|
- name: Assert the Windows install ISO exists
|
|
ansible.builtin.stat:
|
|
path: "{{ win_vm_iso }}"
|
|
register: win_iso_stat
|
|
failed_when: not win_iso_stat.stat.exists
|
|
|
|
- name: Check whether the libvirt domain already exists
|
|
ansible.builtin.command: "virsh dominfo {{ win_vm_name }}"
|
|
register: win_dominfo
|
|
changed_when: false
|
|
failed_when: false
|
|
|
|
- name: Create the Windows VM
|
|
when: win_dominfo.rc != 0
|
|
block:
|
|
- name: Check whether the root-disk zvol already exists
|
|
ansible.builtin.command: "zfs list -H -o name {{ win_vm_zvol }}"
|
|
register: win_zvol_check
|
|
changed_when: false
|
|
failed_when: false
|
|
|
|
- name: Create the root-disk zvol
|
|
ansible.builtin.command:
|
|
cmd: >-
|
|
zfs create -V {{ win_vm_disk_gb }}G
|
|
-o volblocksize={{ win_vm_zvol_volblocksize }}
|
|
{{ win_vm_zvol }}
|
|
when: win_zvol_check.rc != 0
|
|
|
|
- name: Wait for the zvol device node
|
|
ansible.builtin.wait_for:
|
|
path: "{{ win_vm_zvol_dev }}"
|
|
timeout: 30
|
|
|
|
- name: Render autounattend.xml
|
|
ansible.builtin.template:
|
|
src: autounattend.xml.j2
|
|
dest: "/var/lib/libvirt/images/{{ win_vm_name }}-autounattend.xml"
|
|
mode: "0600"
|
|
no_log: true # contains the local admin password
|
|
|
|
- name: Build the autounattend seed ISO (label AUTOUNATTEND)
|
|
ansible.builtin.command:
|
|
cmd: >-
|
|
genisoimage -output /var/lib/libvirt/images/{{ win_vm_name }}-unattend.iso
|
|
-volid AUTOUNATTEND -joliet -rock -graft-points
|
|
autounattend.xml=/var/lib/libvirt/images/{{ win_vm_name }}-autounattend.xml
|
|
args:
|
|
creates: "/var/lib/libvirt/images/{{ win_vm_name }}-unattend.iso"
|
|
|
|
- name: Define and start the VM (UEFI, virtio disk + NIC, virtio-win attached)
|
|
ansible.builtin.command:
|
|
cmd: >-
|
|
virt-install
|
|
--name {{ win_vm_name }}
|
|
--memory {{ win_vm_memory_mb }}
|
|
--vcpus {{ win_vm_vcpus }}
|
|
--machine q35
|
|
--boot loader=/usr/share/OVMF/OVMF_CODE_4M.fd,loader.readonly=yes,loader.type=pflash,nvram.template=/usr/share/OVMF/OVMF_VARS_4M.fd
|
|
--osinfo require=off,name=win2k25
|
|
--disk path={{ win_vm_zvol_dev }},format=raw,bus=virtio,boot.order=2
|
|
--disk path={{ win_vm_iso }},device=cdrom,bus=sata,boot.order=1
|
|
--disk path=/var/lib/libvirt/images/{{ win_vm_name }}-unattend.iso,device=cdrom,bus=sata
|
|
--disk path={{ win_vm_virtio_iso }},device=cdrom,bus=sata
|
|
--network bridge={{ win_vm_bridge }},model=virtio
|
|
--video vga --graphics vnc,listen=0.0.0.0
|
|
--noautoconsole --import
|
|
register: win_virt_install
|
|
|
|
- name: Press a key past "Press any key to boot from CD" (first boot only)
|
|
ansible.builtin.shell: >-
|
|
for i in $(seq 1 20); do
|
|
virsh send-key {{ win_vm_name }} --codeset linux KEY_ENTER >/dev/null 2>&1 || true;
|
|
sleep 2;
|
|
done
|
|
changed_when: false
|
|
|
|
- name: Wait for WinRM (Windows Setup runs unattended, then configures WinRM)
|
|
ansible.builtin.wait_for:
|
|
host: "{{ win_vm_ip }}"
|
|
port: 5986
|
|
delay: 60
|
|
timeout: 2700 # up to 45 min: install + reboots + first-logon commands
|
|
when: win_dominfo.rc != 0
|
|
|
|
- name: Eject install media and remove the (password-bearing) seed ISO
|
|
when: win_dominfo.rc != 0
|
|
block:
|
|
- name: Eject install media (win ISO=sda, unattend=sdb, virtio=sdc)
|
|
ansible.builtin.command: "virsh change-media {{ win_vm_name }} {{ item }} --eject --config"
|
|
loop: [sda, sdb, sdc]
|
|
failed_when: false
|
|
changed_when: true
|
|
|
|
- name: Delete the autounattend seed ISO + rendered answer file
|
|
ansible.builtin.file:
|
|
path: "{{ item }}"
|
|
state: absent
|
|
loop:
|
|
- "/var/lib/libvirt/images/{{ win_vm_name }}-unattend.iso"
|
|
- "/var/lib/libvirt/images/{{ win_vm_name }}-autounattend.xml"
|