platform/platform-infra/ansible/group_vars/all.yml
Bart Van Geyt d715244b76 Phase 1: Ansible host baseline for Ubuntu VM
Idempotent host configuration targeting Ubuntu 24.04 with ZFS on a
dedicated second disk. Role-based platform-infra/ansible:

- base: apt packages, timezone, unattended security upgrades.
- zfs: install ZFS, create pool on a dedicated disk (guarded against
  wiping a non-empty disk), create platform datasets + customers parent
  per docs/03; docker dataset mounted at /var/lib/docker.
- docker: Docker Engine + Compose plugin, daemon.json written before first
  start so the native zfs storage driver initializes on the ZFS data-root;
  per-site network address pool preconfigured.
- firewall: nftables inbound default-deny in a dedicated table that never
  flushes Docker's rules; container outbound SMTP blocked via a DOCKER-USER
  jump applied by a systemd oneshot.
- ssh_hardening: key-first SSH with an anti-lockout assertion, config
  validation gate, and the sftponly group for Phase 4 SFTP accounts.

Includes ansible.cfg, requirements.yml, inventory example, group_vars with
safety notes, and a run guide. Real inventory (hosts.yml) is git-ignored.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-07 12:45:42 +02:00

56 lines
3 KiB
YAML

# ─────────────────────────────────────────────────────────────────────────────
# heleos platform — host baseline variables (Phase 1)
# Edit these to match your environment before running the playbook.
# ─────────────────────────────────────────────────────────────────────────────
# --- General ----------------------------------------------------------------
host_timezone: "Europe/Brussels"
# --- ZFS --------------------------------------------------------------------
# The pool is created on a DEDICATED second virtual disk. Attach a disk to the
# VM first (e.g. /dev/sdb or /dev/vdb) and set it here.
#
# ⚠️ zpool create is DESTRUCTIVE to the target disk. The playbook refuses to
# touch a disk that already contains a filesystem/partition unless you set
# zfs_pool_force: true. For production prefer a stable /dev/disk/by-id/... path.
zfs_pool_name: tank
zfs_pool_disk: /dev/sdb
zfs_pool_force: false
zfs_compression: lz4 # lz4 (fast) or zstd (denser)
# Datasets created under the pool. Web roots and per-site/customer datasets are
# created later by the provisioning CLI (Phase 4); here we create the fixed
# platform datasets + the customers parent. See docs/03-naming-conventions.md.
zfs_child_datasets:
- { path: "platform" }
- { path: "platform/docker", mountpoint: "/var/lib/docker" }
- { path: "platform/mariadb" }
- { path: "platform/db-backups" }
- { path: "platform/traefik" }
- { path: "platform/forgejo" }
- { path: "platform/monitoring" }
- { path: "customers" }
# --- Docker -----------------------------------------------------------------
# Native ZFS storage driver keeps image layers as ZFS datasets under the pool
# (data-root sits on tank/platform/docker). Switch to overlay2 only if you have
# a specific reason.
docker_storage_driver: zfs
docker_data_root: /var/lib/docker
# Address pool for the many per-site bridge networks (avoids subnet exhaustion).
docker_address_pool_base: "10.201.0.0/16"
docker_address_pool_size: 24
# --- Firewall (nftables + Docker egress) ------------------------------------
ssh_port: 22
firewall_allowed_tcp_ports: [80, 443] # SSH is added automatically via ssh_port
# Outbound SMTP from containers is blocked (spam prevention from hacked sites).
smtp_blocked_ports: [25, 465, 587]
smtp_relay_host: "" # optional: allow SMTP only to this host
# --- SSH hardening ----------------------------------------------------------
# ⚠️ If ssh_disable_password_auth is true you MUST provide admin_authorized_keys
# for admin_user, or you will lock yourself out. The playbook asserts this.
admin_user: "{{ ansible_user }}"
admin_authorized_keys: [] # list of public key strings
ssh_disable_password_auth: false # flip to true once key login is verified