Restructure terraform workspaces and deploy minio s3 backend

This commit is contained in:
Sho Ishida 2026-07-19 11:16:22 +00:00
parent 8506f12bce
commit caa7316a2b
11 changed files with 450 additions and 7 deletions

18
.gitignore vendored
View File

@ -5,17 +5,21 @@ ansible/playbooks/*.retry
*.retry
# === Terraform ===
terraform/.terraform/
terraform/.terraform.lock.*
.terraform/
.terraform.lock.hcl
*.terraform.lock.*
crash.log
*.crash.log
# === State Files ===
terraform/terraform.tfstate
terraform/terraform.tfstate.backup
terraform/terraform.tfstate.d/
*.tfstate
*.tfstate.*
terraform.tfstate
terraform.tfstate.*
# === Variables ===
terraform/*.tfvars
terraform/*.tfvars.json
*.tfvars
*.tfvars.json
# === OS & IDE ===
.DS_Store

View File

@ -7,6 +7,7 @@ lan_subnet: "172.30.1.0/24"
host_ip: "172.30.1.200"
gateway_ip: "172.30.1.254"
utility_ip: "172.30.1.80"
freeipa_ip: "172.30.1.85"
portfolio_ip: "172.30.1.93"
minecraft_ip: "172.30.1.91"
@ -20,3 +21,9 @@ admin_user: "sho"
ipa_admin_password: "ChangeMeIPAAdmin123!"
ipa_directory_manager_password: "ChangeMeIPAAdmin123!"
minio_root_user: "admin"
minio_root_password: "ChangeThisPasswordSecurely"
minio_port: "9000"
minio_console_port: "9001"
minio_data_dir: "/home/{{ admin_user }}/containers/minio/data"

View File

@ -2,6 +2,7 @@
hypervisor.lab.local ansible_host=172.30.1.200 ansible_user=sho
[vms]
utility.lab.local ansible_host=172.30.1.80 ansible_user=sho
freeipa.lab.local ansible_host=172.30.1.85 ansible_user=sho
portfolio.lab.local ansible_host=172.30.1.93 ansible_user=sho
minecraft.lab.local ansible_host=172.30.1.91 ansible_user=sho

View File

@ -0,0 +1,65 @@
---
- name: Deploy MinIO Infrastructure on Utility VM
hosts: utility.lab.local
gather_facts: true
become: false
tasks:
- name: Install Podman and rootless container dependencies
become: true
ansible.builtin.package:
name:
- podman
- uidmap
- dbus-user-session
state: present
- name: Create MinIO directory structures
ansible.builtin.file:
path: "{{ item }}"
state: directory
owner: "{{ admin_user }}"
group: "{{ admin_user }}"
mode: "0755"
loop:
- "/home/{{ admin_user }}/containers/minio"
- "{{ minio_data_dir }}"
- name: Deploy MinIO Systemd Service
become: true
ansible.builtin.template:
src: "./templates/minio.service.j2"
dest: "/etc/systemd/system/minio.service"
mode: "0644"
- name: Start and enable MinIO service
become: true
ansible.builtin.systemd_service:
name: minio.service
state: restarted
enabled: true
daemon_reload: true
- name: Wait for MinIO API to be ready
ansible.builtin.wait_for:
port: 9000
delay: 2
timeout: 30
- name: Install MinIO client (mc)
become: true
ansible.builtin.get_url:
url: "https://dl.min.io/client/mc/release/linux-amd64/mc"
dest: "/usr/local/bin/mc"
mode: "0755"
- name: Configure mc local alias
ansible.builtin.command:
cmd: "/usr/local/bin/mc alias set localhttp http://localhost:9000 {{ minio_root_user }} {{ minio_root_password }}"
changed_when: false
- name: Create 'terraform-state' bucket if it doesn't exist
ansible.builtin.command:
cmd: "/usr/local/bin/mc mb --ignore-existing localhttp/terraform-state"
register: mb_result
changed_when: "'Bucket created successfully' in mb_result.stdout"

View File

@ -0,0 +1,21 @@
[Unit]
Description=MinIO Object Storage Container
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
Restart=always
ExecStartPre=-/usr/bin/podman rm -f minio
ExecStart=/usr/bin/podman run --name minio \
-p 9000:9000 \
-p 9001:9001 \
-v {{ minio_data_dir }}:/data:z,U \
-e "MINIO_ROOT_USER={{ minio_root_user }}" \
-e "MINIO_ROOT_PASSWORD={{ minio_root_password }}" \
quay.io/minio/minio:latest server /data --console-address ":9001"
ExecStop=/usr/bin/podman stop -t 10 minio
ExecStopPost=-/usr/bin/podman rm -f minio
[Install]
WantedBy=multi-user.target

View File

@ -0,0 +1,67 @@
terraform {
required_version = ">=1.5.0"
required_providers {
libvirt = {
source = "dmacvicar/libvirt"
version = "0.7.6"
}
}
}
provider "libvirt" {
uri = "qemu+ssh://sho@172.30.1.200/system"
}
resource "libvirt_volume" "debian12_base" {
name = "debian12-base-bootstrap.qcow2"
pool = "vm_pool"
source = "https://cloud.debian.org/images/cloud/bookworm/latest/debian-12-generic-amd64.qcow2"
format = "qcow2"
}
resource "libvirt_volume" "utility_disk" {
name = "utility-disk.qcow2"
pool = "vm_pool"
base_volume_id = libvirt_volume.debian12_base.id
size = 21474836480
format = "qcow2"
}
data "template_file" "user_data" {
template = file("${path.module}/templates/cloud_init.cfg")
vars = {
admin_user = "sho"
ssh_key = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAILM/84tpkx+yYsA8Zr5or1xuELOGMl0JEP576SyUc9eC sho@bazzite"
}
}
resource "libvirt_cloudinit_disk" "utility_init" {
name = "utility-init.iso"
pool = "vm_pool"
user_data = data.template_file.user_data.rendered
network_config = templatefile("${path.module}/templates/network_config.cfg.tpl", {
interface_name = "ens3"
ip_address = "172.30.1.80"
gateway_ip = "172.30.1.254"
dns_ip = "172.30.1.85"
})
}
resource "libvirt_domain" "utility_vm" {
name = "utility"
memory = "2048"
vcpu = 2
cpu { mode = "host-passthrough" }
cloudinit = libvirt_cloudinit_disk.utility_init.id
network_interface {
bridge = "br0"
mac = "52:54:00:ee:ef:60"
}
disk { volume_id = libvirt_volume.utility_disk.id }
console {
type = "pty"
target_port = "0"
target_type = "serial"
}
}

View File

@ -0,0 +1,15 @@
#cloud-config
package_update: true
package_upgrade: false
users:
- name: ${admin_user}
groups: wheel, systemd-journal
sudo: ["ALL=(ALL) NOPASSWD:ALL"]
shell: /bin/bash
ssh_authorized_keys:
- ${ssh_key}
runcmd:
- sed -i 's/^#PasswordAuthentication yes/PasswordAuthentication no/g' /etc/ssh/sshd_config
- systemctl restart sshd

View File

@ -0,0 +1,14 @@
#cloud-config
version: 2
ethernets:
${interface_name}:
dhcp4: no
addresses:
- ${ip_address}/24
routes:
- to: default
via: ${gateway_ip}
nameservers:
addresses:
- ${dns_ip}
- 1.1.1.1

220
terraform/workloads/main.tf Normal file
View File

@ -0,0 +1,220 @@
terraform {
required_version = ">=1.5.0"
backend "s3" {
bucket = "terraform-state"
key = "workloads/terraform.tfstate"
region = "main"
endpoints = { s3 = "http://172.30.1.80:9000" }
skip_credentials_validation = true
skip_metadata_api_check = true
skip_region_validation = true
skip_requesting_account_id = true
use_path_style = true
}
required_providers {
libvirt = {
source = "dmacvicar/libvirt"
version = "0.7.6"
}
}
}
provider "libvirt" {
uri = "qemu+ssh://sho@172.30.1.200/system"
}
resource "libvirt_volume" "almalinux10_image" {
name = "almalinux10-base.qcow2"
pool = "vm_pool"
source = "https://repo.almalinux.org/almalinux/10/cloud/x86_64/images/AlmaLinux-10-GenericCloud-latest.x86_64.qcow2"
format = "qcow2"
}
resource "libvirt_volume" "debian12_image" {
name = "debian12-base.qcow2"
pool = "vm_pool"
source = "https://cloud.debian.org/images/cloud/bookworm/latest/debian-12-generic-amd64.qcow2"
format = "qcow2"
}
resource "libvirt_volume" "freeipa_disk" {
name = "freeipa-disk.qcow2"
pool = "vm_pool"
base_volume_id = libvirt_volume.almalinux10_image.id
size = 42949672960
format = "qcow2"
}
resource "libvirt_volume" "portfolio_disk" {
name = "portfolio-disk.qcow2"
pool = "vm_pool"
base_volume_id = libvirt_volume.debian12_image.id
size = 10737418240
format = "qcow2"
}
resource "libvirt_volume" "minecraft_disk" {
name = "minecraft-disk.qcow2"
pool = "vm_pool"
base_volume_id = libvirt_volume.debian12_image.id
size = 21474836480
format = "qcow2"
}
resource "libvirt_volume" "navidrome_disk" {
name = "navidrome-disk.qcow2"
pool = "vm_pool"
base_volume_id = libvirt_volume.debian12_image.id
size = 16106127360
format = "qcow2"
}
data "template_file" "user_data" {
template = file("${path.module}/templates/cloud_init.cfg")
vars = {
admin_user = "sho"
ssh_key = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAILM/84tpkx+yYsA8Zr5or1xuELOGMl0JEP576SyUc9eC sho@bazzite"
}
}
resource "libvirt_cloudinit_disk" "freeipa_init" {
name = "freeipa-init.iso"
pool = "vm_pool"
user_data = data.template_file.user_data.rendered
network_config = templatefile("${path.module}/templates/network_config.cfg.tpl", {
interface_name = "etho0"
ip_address = "172.30.1.85"
gateway_ip = "172.30.1.254"
dns_ip = "172.30.1.85"
})
}
resource "libvirt_cloudinit_disk" "portfolio_init" {
name = "portfolio-init.iso"
pool = "vm_pool"
user_data = data.template_file.user_data.rendered
network_config = templatefile("${path.module}/templates/network_config.cfg.tpl", {
interface_name = "ens3"
ip_address = "172.30.1.93"
gateway_ip = "172.30.1.254"
dns_ip = "172.30.1.85"
})
}
resource "libvirt_cloudinit_disk" "minecraft_init" {
name = "minecraft-init.iso"
pool = "vm_pool"
user_data = data.template_file.user_data.rendered
network_config = templatefile("${path.module}/templates/network_config.cfg.tpl", {
interface_name = "ens3"
ip_address = "172.30.1.91"
gateway_ip = "172.30.1.254"
dns_ip = "172.30.1.85"
})
}
resource "libvirt_cloudinit_disk" "navidrome_init" {
name = "navidrome-init.iso"
pool = "vm_pool"
user_data = data.template_file.user_data.rendered
network_config = templatefile("${path.module}/templates/network_config.cfg.tpl", {
interface_name = "ens3"
ip_address = "172.30.1.92"
gateway_ip = "172.30.1.254"
dns_ip = "172.30.1.85"
})
}
resource "libvirt_domain" "freeipa_vm" {
name = "freeipa"
memory = "3072"
vcpu = 2
cpu { mode = "host-passthrough" }
cloudinit = libvirt_cloudinit_disk.freeipa_init.id
network_interface {
bridge = "br0"
mac = "52:54:00:ee:ef:61"
}
console {
type = "pty"
target_port = "0"
target_type = "serial"
}
disk { volume_id = libvirt_volume.freeipa_disk.id }
graphics {
type = "spice"
listen_type = "address"
autoport = true
}
}
resource "libvirt_domain" "portfolio_vm" {
name = "portfolio"
memory = "1024"
vcpu = 1
cpu { mode = "host-passthrough" }
cloudinit = libvirt_cloudinit_disk.portfolio_init.id
network_interface {
bridge = "br0"
mac = "52:54:00:ee:ef:62"
}
console {
type = "pty"
target_port = "0"
target_type = "serial"
}
disk { volume_id = libvirt_volume.portfolio_disk.id }
graphics {
type = "spice"
listen_type = "address"
autoport = true
}
}
resource "libvirt_domain" "minecraft_vm" {
name = "minecraft"
memory = "6144"
vcpu = 2
cpu { mode = "host-passthrough" }
cloudinit = libvirt_cloudinit_disk.minecraft_init.id
network_interface {
bridge = "br0"
mac = "52:54:00:ee:ef:63"
}
console {
type = "pty"
target_port = "0"
target_type = "serial"
}
disk { volume_id = libvirt_volume.minecraft_disk.id }
graphics {
type = "spice"
listen_type = "address"
autoport = true
}
}
resource "libvirt_domain" "navidrome_vm" {
name = "navidrome"
memory = "1024"
vcpu = 1
cpu { mode = "host-passthrough" }
cloudinit = libvirt_cloudinit_disk.navidrome_init.id
network_interface {
bridge = "br0"
mac = "52:54:00:ee:ef:65"
}
console {
type = "pty"
target_port = "0"
target_type = "serial"
}
disk { volume_id = libvirt_volume.navidrome_disk.id }
graphics {
type = "spice"
listen_type = "address"
autoport = true
}
}

View File

@ -0,0 +1,15 @@
#cloud-config
package_update: true
package_upgrade: false
users:
- name: ${admin_user}
groups: wheel, systemd-journal
sudo: ["ALL=(ALL) NOPASSWD:ALL"]
shell: /bin/bash
ssh_authorized_keys:
- ${ssh_key}
runcmd:
- sed -i 's/^#PasswordAuthentication yes/PasswordAuthentication no/g' /etc/ssh/sshd_config
- systemctl restart sshd

View File

@ -0,0 +1,14 @@
#cloud-config
version: 2
ethernets:
${interface_name}:
dhcp4: no
addresses:
- ${ip_address}/24
routes:
- to: default
via: ${gateway_ip}
nameservers:
addresses:
- ${dns_ip}
- 1.1.1.1