3.2 KiB
Ansible deploy
One playbook does both jobs: the first run provisions the host (Docker, WireGuard, sysctl, firewall) and deploys the stack; every later run is the update path — it only touches what changed and restarts only the affected services.
Deployed layout on the VPS (per-service dirs under /opt):
| Path | Contents |
|---|---|
/opt/vpnhub/ |
docker-compose.yml, .env |
/opt/openvpn/ |
build context, server.conf, pki/ |
/opt/duo-authproxy/ |
build context, cfg template, certs/ |
/opt/technitium/ |
init-job build context + config/ (live zone DB — never overwritten by the playbook) |
The playbook renders the firewall and wg0 config from the same
host/rules.v4.template / host/wg0.conf.example files the manual path
uses — nothing is duplicated inside ansible/.
Prerequisites
A Linux control node (WSL is fine — this repo checked out inside WSL or
accessed via /mnt/c/...), ansible-core >= 2.15, then:
cd ansible
ansible-galaxy collection install -r requirements.yml
First-time setup
cp inventory.example.yml inventory.yml # set host/user
cp group_vars/vpnhub.example.yml group_vars/vpnhub.yml
$EDITOR group_vars/vpnhub.yml # DC IPs, Duo keys, secrets
ansible-vault encrypt group_vars/vpnhub.yml # both files are gitignored anyway
# Local key material (both gitignored, synced to /opt by the playbook):
# ../openvpn/pki/ server.crt, server.key, ta.key (offline CA)
# ../duo-authproxy/certs/ ad-ldaps-ca.pem
ansible-playbook site.yml
The first run prints the hub WireGuard public key and stops short of
starting wg0 (site peer keys are still empty). Add the hub as a peer at
both sites (docs/SITE-SIDE.md), paste each site's public key into
group_vars/vpnhub.yml (troch_wg_public_key / oswald_wg_public_key),
and run it again — wg0 comes up and the stack starts.
Updating
| What changed | Command |
|---|---|
Any config in the repo, .env values |
ansible-playbook site.yml (affected services recreate) |
| Just stack files, skip host checks | ansible-playbook site.yml --tags stack |
| Base images / rebuild everything | ansible-playbook site.yml -e vpnhub_force_rebuild=true |
| Duo Auth Proxy version | bump duo_authproxy_version, then force-rebuild as above |
| Firewall only | ansible-playbook site.yml --tags firewall |
| WireGuard peers/config | ansible-playbook site.yml --tags wireguard |
Note on duo_authproxy_version: latest: Docker's layer cache means
"latest" won't re-download a newer tarball on rebuild. Pin a real version
(the cache busts when it changes) — that's the reliable update mechanism.
Tags
docker, host (packages + sysctl + firewall + wg), firewall,
wireguard, stack.