Add bolt scripting to create VMs

This commit is contained in:
moeny-matt 2024-11-21 15:35:42 -05:00
parent aecb97e68f
commit ec854a9c27
12 changed files with 355 additions and 2 deletions

1
.gitignore vendored Normal file
View File

@ -0,0 +1 @@
.DS_Store

View File

@ -8,6 +8,8 @@ Note that the following steps are derived from this [guide](https://www.pugetsys
[Autoinstall configuration reference manual](https://canonical-subiquity.readthedocs-hosted.com/en/latest/reference/autoinstall-reference.html)
## Generating the autoinstall ISO
1. Install necessary packages
```bash
@ -111,4 +113,17 @@ sudo apt install yamllint
yamllint server/user-data
```
Once the `xorriso` command is run successfully, the `ubuntu-22.04-autoinstall.iso` will be created in the `iso-build` directory.
Once the `xorriso` command is run successfully, the `ubuntu-22.04-autoinstall.iso` will be created in the `iso-build` directory.
## Creating the VM using Bolt
Update the parameters provided to the below plan run command as needed.
```bash
cd bolt_vm_automation
bolt plan run bolt_vm_automation::create_vm \
target=roscoe \
vm_name=moeny-bank01 \
ip_with_cidr=100.40.223.189/24 \
hostname=moeny-bank01
```

7
bolt_vm_automation/.gitignore vendored Normal file
View File

@ -0,0 +1,7 @@
.modules/
.resource_types/
bolt-debug.log
.plan_cache.json
.plugin_cache.json
.task_cache.json
.rerun.json

View File

@ -0,0 +1,2 @@
---
name: bolt_vm_automation

View File

@ -0,0 +1,32 @@
groups:
- name: remote-host
targets:
- name: roscoe
config:
transport: ssh
ssh:
host: 100.40.223.136
user: root
host-key-check: false
- name: siderack
config:
transport: ssh
ssh:
host: 100.40.223.138
user: root
host-key-check: false
- name: new-vm
targets:
- name: vm-template-staging
config:
transport: ssh
ssh:
host: 100.40.223.190
user: moeny
private-key: ~/.ssh/DMMF-20211104
host-key-check: false
config:
ssh:
native-ssh: true

View File

@ -0,0 +1,95 @@
---
parameters:
target:
type: String
description: "Target host to create the VM on"
default: "roscoe"
iso_path:
type: String
description: "Path to the ISO file"
default: "/mnt/nfs/kvm-isos/iso-build/ubuntu-22.04-autoinstall.iso"
vm_name:
type: String
description: "Name of the VM"
default: "vm-template-staging"
ram:
type: Integer
description: "Amount of RAM in MB"
default: 2048
vcpus:
type: Integer
description: "Number of virtual CPUs"
default: 4
disk_size:
type: Integer
description: "Size of the disk in GB"
default: 100
disk_path:
type: String
description: "Base path for disk images"
default: "/mnt/nfs/kvm-images"
network:
type: String
description: "Network to connect the VM to"
default: "wan-verizon"
ip_with_cidr:
type: String
description: "Public IP of the VM"
default: "100.40.223.190/24"
hostname:
type: String
description: "Hostname of the VM"
default: "vm-template-staging"
dhcp:
type: Boolean
description: "Enable DHCP on the VM"
default: false
gateway:
type: String
description: "Gateway for the VM"
default: "100.40.223.1"
nameserver1:
type: String
description: "Primary nameserver for the VM"
default: "8.8.8.8"
nameserver2:
type: String
description: "Secondary nameserver for the VM"
default: "8.8.4.4"
nameserver3:
type: String
description: "Tertiary nameserver for the VM"
default: "1.1.1.1"
steps:
- name: create_vm
task: bolt_vm_automation::create_vm
targets: $target
parameters:
iso_path: $iso_path
vm_name: $vm_name
ram: $ram
vcpus: $vcpus
disk_size: $disk_size
disk_path: "${disk_path}/${vm_name}.qcow2"
network: $network
- name: install_docker
description: Install Docker on the VM
task: bolt_vm_automation::install_docker
targets: vm-template-staging
- name: system_setup
task: bolt_vm_automation::system_setup
targets: vm-template-staging
parameters:
ip_with_cidr: $ip_with_cidr
hostname: $hostname
dhcp: $dhcp
gateway: $gateway
nameserver1: $nameserver1
nameserver2: $nameserver2
nameserver3: $nameserver3
return:
message: "VM ${vm_name} created and updated successfully!"

View File

@ -0,0 +1,40 @@
{
"description": "Creates a new VM using virt-install",
"parameters": {
"iso_path": {
"type": "String",
"description": "Path to the autoinstall ISO",
"default": "/mnt/nfs/kvm-isos/iso-build/ubuntu-22.04-autoinstall.iso"
},
"vm_name": {
"type": "String",
"description": "Name of the VM",
"default": "vm-template-staging"
},
"ram": {
"type": "Integer",
"description": "Amount of RAM in MB",
"default": 2048
},
"vcpus": {
"type": "Integer",
"description": "Number of virtual CPUs",
"default": 4
},
"disk_size": {
"type": "Integer",
"description": "Size of the VM disk in GB",
"default": 100
},
"disk_path": {
"type": "String",
"description": "Base path for disk images",
"default": "/mnt/nfs/kvm-images/vm-template-staging.qcow2"
},
"network": {
"type": "String",
"description": "Network to connect the VM to",
"default": "wan-verizon"
}
}
}

View File

@ -0,0 +1,31 @@
#!/bin/bash
# Input Variables
ISO_PATH=$PT_iso_path
VM_NAME=$PT_vm_name
RAM=$PT_ram
VCPUS=$PT_vcpus
DISK_SIZE=$PT_disk_size
DISK_PATH=$PT_disk_path
NETWORK=$PT_network
# Create VM disk if not already exists
if [ ! -f "$DISK_PATH" ]; then
qemu-img create -f qcow2 "$DISK_PATH" "$DISK_SIZE"G > /dev/null 2>&1
fi
# Create VM
virt-install \
--name "$VM_NAME" \
--ram "$RAM" \
--vcpus "$VCPUS" \
--os-variant ubuntu22.04 \
--disk path="$DISK_PATH",format=qcow2 \
--cdrom "$ISO_PATH" \
--network network="$NETWORK" \
--graphics vnc \
--noautoconsole \
--autostart \
--wait -1
sleep 45

View File

@ -0,0 +1,39 @@
#!/bin/bash
# Update package list and install prerequisites
sudo apt-get update
sudo apt-get install -y \
ca-certificates \
curl \
gnupg
# Add Docker's official GPG key
sudo install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
sudo chmod a+r /etc/apt/keyrings/docker.gpg
# Add the repository to Apt sources
echo \
"deb [arch="$(dpkg --print-architecture)" signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu \
"$(. /etc/os-release && echo "$VERSION_CODENAME")" stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
# Update package list again and install Docker
sudo apt-get update
sudo apt-get install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
# Add current user to docker group
sudo usermod -aG docker "$USER"
# Start and enable Docker service
sudo systemctl start docker
sudo systemctl enable docker
# Verify installation
if docker --version > /dev/null 2>&1; then
echo "Docker installed successfully"
exit 0
else
echo "Docker installation failed"
exit 1
fi

View File

@ -0,0 +1,40 @@
{
"description": "Configures system network settings using netplan",
"parameters": {
"ip_with_cidr": {
"type": "String",
"description": "IP address for the VM",
"default": "100.40.223.190/24"
},
"hostname": {
"type": "String",
"description": "Hostname for the VM",
"default": "vm-template-staging"
},
"dhcp": {
"type": "Boolean",
"description": "Whether to use DHCP for network configuration",
"default": false
},
"gateway": {
"type": "String",
"description": "Gateway IP address",
"default": "100.40.223.1"
},
"nameserver1": {
"type": "String",
"description": "Primary DNS nameserver",
"default": "8.8.8.8"
},
"nameserver2": {
"type": "String",
"description": "Secondary DNS nameserver",
"default": "8.8.4.4"
},
"nameserver3": {
"type": "String",
"description": "Tertiary DNS nameserver",
"default": "1.1.1.1"
}
}
}

View File

@ -0,0 +1,51 @@
#!/bin/bash
# Using Bolt's environment variables
IP="${PT_ip_with_cidr}"
HOSTNAME="${PT_hostname}"
DHCP="${PT_dhcp}"
GATEWAY="${PT_gateway}"
NAMESERVER1="${PT_nameserver1}"
NAMESERVER2="${PT_nameserver2}"
NAMESERVER3="${PT_nameserver3}"
# Check if all required parameters are provided
if [ -z "$IP" ] || [ -z "$HOSTNAME" ] || [ -z "$DHCP" ] || [ -z "$GATEWAY" ] || [ -z "$NAMESERVER1" ] || [ -z "$NAMESERVER2" ] || [ -z "$NAMESERVER3" ]; then
echo "Missing required parameters. All parameters must be provided."
exit 1
fi
# Create the new netplan configuration
sudo tee /etc/netplan/50-cloud-init.yaml << EOL
network:
version: 2
ethernets:
enp1s0:
dhcp4: ${DHCP}
EOL
# If DHCP is false, add static IP configuration
if [ "$DHCP" = "false" ]; then
sudo tee -a /etc/netplan/50-cloud-init.yaml << EOL
addresses:
- ${IP}
routes:
- to: default
via: ${GATEWAY}
nameservers:
addresses: [${NAMESERVER1}, ${NAMESERVER2}, ${NAMESERVER3}]
EOL
fi
# Set the hostname
sudo hostnamectl set-hostname "${HOSTNAME}"
echo "${HOSTNAME}" | sudo tee /etc/hostname > /dev/null
# Update /etc/hosts
sudo sed -i "s/127.0.1.1.*/127.0.1.1\t${HOSTNAME}/" /etc/hosts
echo "System configuration completed successfully"
# Apply network configuration in the background and exit before it takes effect
nohup bash -c "(sleep 2 && sudo netplan apply) &" > /dev/null 2>&1
exit 0

View File

@ -43,4 +43,4 @@ autoinstall:
shutdown: reboot
late-commands:
- curtin in-target --target=/target apt-get update
- ["curtin", "in-target", "--target=/target", "--", "/bin/bash", "-c", "echo '%sudo ALL=(ALL) NOPASSWD: ALL' | tee -a /etc/sudoers.d/nopasswd_sudo_group"]