(???) ?xml version="1.0" encoding="UTF-8" standalone="no"?>
(???) svg xmlns="http://www.w3.org/2000/svg" width="1000" height="920" viewBox="0 0 1000 920" font-family="DejaVu Sans, Verdana, sans-serif" font-size="12">
(???) <defs>
(???) <marker id="arrow" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="8" markerHeight="8" orient="auto">
(???) <path d="M 0 0 L 10 5 L 0 10 z" fill="#333"/>
(???) </marker>
(???) <style>
(???) .box { stroke: #333; stroke-width: 1.2; }
(???) .title { font-weight: bold; font-size: 13px; }
(???) .small { font-size: 11px; }
(???) .line { stroke: #333; stroke-width: 1.5; fill: none; marker-end: url(#arrow); }
(???) .label { font-size: 11px; fill: #333; }
(???) .outside { fill: #ffffff; }
(???) .edge { fill: #fde7d4; }
(???) .public { fill: #dbeafe; }
(???) .vpn { fill: #dcfce7; }
(???) .infra { fill: #f3f4f6; }
(???) .vm { stroke-dasharray: 6 3; stroke-width: 1.6; }
(???) </style>
(???) </defs>
(???) <rect width="1000" height="920" fill="#ffffff"/>
(???) <!-- outside world, top -->
(???) <rect class="box outside" x="60" y="20" width="270" height="70" rx="8"/>
(???) <text class="title" x="195" y="50" text-anchor="middle">Internet</text>
(???) <text class="small" x="195" y="70" text-anchor="middle">visitors (and bad bots)</text>
(???) <rect class="box outside" x="360" y="20" width="250" height="70" rx="8"/>
(???) <text class="title" x="485" y="45" text-anchor="middle">Workstation</text>
(???) <text class="small" x="485" y="63" text-anchor="middle">OpenTofu talks to the Incus API</text>
(???) <text class="small" x="485" y="78" text-anchor="middle">over Tailscale, git with sops secrets</text>
(???) <rect class="box outside" x="640" y="20" width="300" height="70" rx="8"/>
(???) <text class="title" x="790" y="50" text-anchor="middle">My devices</text>
(???) <text class="small" x="790" y="70" text-anchor="middle">computer, phone, tablet (trust the root CA)</text>
(???) <!-- server frame -->
(???) <rect class="box" x="20" y="120" width="960" height="680" rx="12" fill="#fafafa" stroke-width="2"/>
(???) <text class="title" x="410" y="142" text-anchor="middle">Laptop server running Incus OS</text>
(???) <text class="small" x="410" y="160" text-anchor="middle">Secure Boot, TPM disk encryption, A/B updates</text>
(???) <text class="small" x="410" y="176" text-anchor="middle">no shell, no SSH, managed only through the Incus API</text>
(???) <!-- edge row -->
(???) <rect class="box edge vm" x="60" y="190" width="270" height="80" rx="8"/>
(???) <text class="title" x="195" y="214" text-anchor="middle">haproxy VM (DMZ)</text>
(???) <text class="small" x="195" y="233" text-anchor="middle">CrowdSec bouncer, drops bad IPs (nftables)</text>
(???) <text class="small" x="195" y="250" text-anchor="middle">raw TCP only, holds no TLS key</text>
(???) <rect class="box edge" x="640" y="190" width="300" height="80" rx="8"/>
(???) <text class="title" x="790" y="214" text-anchor="middle">Tailscale (built into Incus OS)</text>
(???) <text class="small" x="790" y="233" text-anchor="middle">Incus API</text>
(???) <text class="small" x="790" y="250" text-anchor="middle">proxy devices to the VPN sites</text>
(???) <!-- internal bridge -->
(???) <rect x="40" y="290" width="920" height="490" rx="10" fill="none" stroke="#888" stroke-width="1.5" stroke-dasharray="8 4"/>
(???) <text class="small" x="500" y="308" text-anchor="middle" fill="#555">Internal bridge, ACL: everything denied by default, in both directions</text>
(???) <!-- reverse proxies -->
(???) <rect class="box public" x="60" y="330" width="270" height="65" rx="8"/>
(???) <text class="title" x="195" y="355" text-anchor="middle">Caddy (public)</text>
(???) <text class="small" x="195" y="375" text-anchor="middle">Let's Encrypt certificates, TLS 1.3</text>
(???) <rect class="box vpn" x="640" y="330" width="300" height="65" rx="8"/>
(???) <text class="title" x="790" y="355" text-anchor="middle">Caddy (VPN only)</text>
(???) <text class="small" x="790" y="375" text-anchor="middle">certificates from the internal CA</text>
(???) <!-- services -->
(???) <rect class="box public" x="60" y="430" width="270" height="85" rx="8"/>
(???) <text class="title" x="195" y="451" text-anchor="middle">Public services</text>
(???) <text class="small" x="195" y="469" text-anchor="middle">Nextcloud, PeerTube, Forgejo,</text>
(???) <text class="small" x="195" y="485" text-anchor="middle">Vaultwarden, website,</text>
(???) <text class="small" x="195" y="501" text-anchor="middle">Immich (share links only)</text>
(???) <rect class="box infra vm" x="360" y="430" width="250" height="85" rx="8"/>
(???) <text class="title" x="485" y="455" text-anchor="middle">CI runner VM</text>
(???) <text class="small" x="485" y="475" text-anchor="middle">Forgejo Actions jobs</text>
(???) <text class="small" x="485" y="492" text-anchor="middle">Docker in Docker</text>
(???) <rect class="box vpn" x="640" y="430" width="300" height="85" rx="8"/>
(???) <text class="title" x="790" y="451" text-anchor="middle">VPN services</text>
(???) <text class="small" x="790" y="469" text-anchor="middle">Immich, Nextcloud (with its admin API),</text>
(???) <text class="small" x="790" y="485" text-anchor="middle">Kanboard, Uptime Kuma, SmokePing,</text>
(???) <text class="small" x="790" y="501" text-anchor="middle">Alertmanager, other admin interfaces</text>
(???) <!-- support services -->
(???) <rect class="box infra" x="60" y="550" width="270" height="85" rx="8"/>
(???) <text class="title" x="195" y="575" text-anchor="middle">Egress proxy</text>
(???) <text class="small" x="195" y="595" text-anchor="middle">HTTP proxy with a domain allow list</text>
(???) <text class="small" x="195" y="612" text-anchor="middle">apt cache, container registry mirrors</text>
(???) <rect class="box infra" x="360" y="550" width="250" height="85" rx="8"/>
(???) <text class="title" x="485" y="575" text-anchor="middle">Monitoring</text>
(???) <text class="small" x="485" y="595" text-anchor="middle">Prometheus, Loki, Grafana,</text>
(???) <text class="small" x="485" y="612" text-anchor="middle">Alertmanager</text>
(???) <rect class="box infra" x="640" y="550" width="145" height="85" rx="8"/>
(???) <text class="title" x="712" y="575" text-anchor="middle">CrowdSec</text>
(???) <text class="small" x="712" y="595" text-anchor="middle">reads logs in Loki</text>
(???) <text class="small" x="712" y="612" text-anchor="middle">feeds the bouncer</text>
(???) <rect class="box infra" x="800" y="550" width="140" height="85" rx="8"/>
(???) <text class="title" x="870" y="575" text-anchor="middle">restic</text>
(???) <text class="small" x="870" y="595" text-anchor="middle">daily backups</text>
(???) <text class="small" x="870" y="612" text-anchor="middle">of the data volumes</text>
(???) <!-- what every instance looks like -->
(???) <rect class="box" x="360" y="665" width="425" height="95" rx="8" fill="#fffbea"/>
(???) <text class="title" x="572" y="688" text-anchor="middle">Inside every system container</text>
(???) <text class="small" x="572" y="707" text-anchor="middle">unprivileged Ubuntu, rebuilt from scratch by cloud-init</text>
(???) <text class="small" x="572" y="723" text-anchor="middle">applications in a podman pod (quadlets), vector log sidecar</text>
(???) <text class="small" x="572" y="739" text-anchor="middle">its own age key to decrypt only its own secrets</text>
(???) <text class="small" x="572" y="755" text-anchor="middle">data on separate volumes with ZFS snapshots</text>
(???) <!-- outside world, bottom -->
(???) <rect class="box outside" x="60" y="830" width="270" height="70" rx="8"/>
(???) <text class="title" x="195" y="858" text-anchor="middle">Allowed upstream</text>
(???) <text class="small" x="195" y="878" text-anchor="middle">apt repositories, registries, allowed domains</text>
(???) <rect class="box outside" x="760" y="830" width="180" height="70" rx="8"/>
(???) <text class="title" x="850" y="858" text-anchor="middle">S3 storage</text>
(???) <text class="small" x="850" y="878" text-anchor="middle">with versioning</text>
(???) <!-- arrows: public path -->
(???) <path class="line" d="M 195 90 L 195 188"/>
(???) <text class="label" x="203" y="150">80/443</text>
(???) <path class="line" d="M 195 270 L 195 328"/>
(???) <text class="label" x="203" y="325">TCP + PROXY protocol</text>
(???) <path class="line" d="M 195 395 L 195 428"/>
(???) <!-- arrows: VPN path -->
(???) <path class="line" d="M 790 90 L 790 188"/>
(???) <text class="label" x="798" y="150">Tailscale VPN</text>
(???) <path class="line" d="M 790 270 L 790 328"/>
(???) <text class="label" x="798" y="325">PROXY protocol</text>
(???) <path class="line" d="M 790 395 L 790 428"/>
(???) <!-- arrow: administration -->
(???) <path class="line" d="M 485 90 L 485 105 L 625 105 L 625 230 L 638 230"/>
(???) <!-- arrows: egress and backups -->
(???) <path class="line" d="M 195 635 L 195 828"/>
(???) <text class="label" x="203" y="815">only allowed domains</text>
(???) <path class="line" d="M 870 635 L 870 828"/>
(???) <text class="label" x="878" y="815">encrypted</text>
(???) /svg>