Files
doc/README.md
T
2026-08-28 15:56:44 +02:00

111 lines
6.3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Personal infrastructure notes
**Start here**:
- [backup-strategy.md](backup-strategy.md) — what is
backed up, by which tool, on what schedule, and how to restore.
- [new-container.md](new-container.md) — conventions for adding a
service to ks4 (and getting it backed up automatically).
**Tech notes**
- [`nuc/`](nuc/) — home lab on `nuc` (see below)
- [`ks4/`](ks4/) — prod server `ks4` at OVH (see below)
- [`ks2/`](ks2/) — legacy backup server being [decommissioned](ks2/plan.md)
- [`archer-c7/`](archer-c7/) — home router (TP-Link Archer C7 v5 running on OpenWrt)
## Homelab: nuc
Incus host on the LAN.
- Debian 13, Intel Alder Lake-N (iGPU `i915`, shared by both Jellyfin containers) —
bare-metal reinstall: [nuc/nuc-install.md](nuc/nuc-install.md)
- Instances are bridged onto the LAN (192.168.0.0/24)
- USB 4 TB WD Red: ZFS pool `usb4t``usb4t/backup``/backup`
(incus exports, `nuc/` + `ks4/` subdatasets, 1 TB quota) and
`usb4t/media``/srv/media` (media library, shared into containers
via `shift=true` disk devices; works because ZFS ≥ 2.2 supports
idmapped mounts)
- Backups: all local instances replicated to the USB pool
(`/root/scripts/incus-copy.sh -p backup -s nucbackup`; replicas
stopped, autostart off) — see
[nuc/nuc-install.md](nuc/nuc-install.md); ks4 replicas pulled into
pool `ks4backup` — see [ks4/incus-copy.md](ks4/incus-copy.md)
### Instances
| Name | IP | Doc | Features |
|---|---|---|---|
| [jellyfin-server](nuc/jellyfin-server.md) | 192.168.0.5 | ✅ | unprivileged, autostart; iGPU render node (`gpu` device, render gid) for QSV/VAAPI transcoding; `/srv/media` disk device (`shift=true`); proxy device → host :8096 |
| [jellyfin-client](nuc/jellyfin-client.md) | 192.168.0.6 | ✅ | **privileged**, autostart; full iGPU (`gpu` device, gid 44) → HDMI kiosk (cage + Jellyfin Media Player); custom `raw.lxc` (bind `/dev/snd`, `/dev/input`, host `/run/udev`); Pioneer USB audio as ALSA default; FR keymap; go-librespot Spotify Connect ("Pioneer A-70") |
| [transmission-bt](nuc/transmission-bt.md) | 192.168.0.7 | ✅ | unprivileged, autostart; always-on WireGuard full tunnel → ks4 (egress = 193.70.35.17, kill switch: no default route); `/srv/media` disk device (`shift=true`), downloads to `/media/downloads`; web UI :9091 (LAN only) |
| blocky | 192.168.0.254 | — | unprivileged, autostart; DNS ad-blocker |
| privoxy | 192.168.0.11 | — | unprivileged, autostart; filtering HTTP proxy |
| homeassistant | (stopped) | — | **virtual machine**, 50 GiB root disk on pool `data` |
## Prod: ks4
Incus host at OVH — public-facing self-hosted services.
- Debian 13, Xeon D-1521 / 32 GiB, 2× 6 TB (OS on mdraid RAID1,
ZFS pool `data` on `sda5`) — setup & rebuild:
[ks4/install.md](ks4/install.md)
- SSH: `ssh -i id_rsa_claude -p 2233 julien@193.70.35.17`
(`julien` has passwordless `sudo incus …`)
- Instances are on a NAT bridge `incusbr0` (192.168.1.0/24); public
ingress via Incus proxy devices. `gateway` (nginx) is the sole HTTP/S
entry point and fans out to the app containers.
- Services: gateway, mail, nextcloud, seafile, git, freshrss, bitwarden,
outline, login (SSO), wireguard, + more — full table in
[ks4/install.md](ks4/install.md).
- ⚠️ The ZFS `data` pool is single-disk (not mirrored); durability
rests on nightly cron jobs — 01:00 `incus copy --refresh` of all
instances to the local `backup` pool on sdb5, then the instance leg
to S3; 05:00 restic (DB dumps + data trees) to S3; nuc pulls the
replicas over WireGuard. Full picture and restore procedures:
**[backup-strategy.md](backup-strategy.md)**
([ks4/local-backup-cron.md](ks4/local-backup-cron.md),
[ks4/incus-copy.md](ks4/incus-copy.md),
[ks4/restic-backup.md](ks4/restic-backup.md)).
## Network flows
```
nuc — home LAN 192.168.0.0/24 ks4 — OVH 193.70.35.17
+-----------------------------------+ +-------------------------------------+
| | | |
| host: wg-ks4 (10.8.0.20) | | [wireguard] 192.168.1.18 |
| incus remote "ks4" ------+--WG-->| wg0 10.8.0.1/24, udp 51845 |
| pull ks4:* -> pool ks4backup | udp | | masquerade -> eth0 |
| on usb4t [pending FTTH seed] | 51845 | | |
| | | +-> incus API 192.168.1.1:8443 |
| [transmission-bt] wg0 (10.8.0.21) | | | (ufw: only from .18) |
| full tunnel 0.0.0.0/0 ------+--WG-->| | |
| kill switch: no default route | udp | +-> WAN egress: torrents + |
| downloads -> /srv/media | 51845 | apt of transmission-bt |
| (usb4t/media, read by jellyfin) | | exit as 193.70.35.17 |
| | | |
| 03:00 instance snapshots | | 03:00 instance snapshots |
| 03:30 incus-copy: all instances | | 01:00 incus-copy: all instances |
| -> project backup, pool | | -> project backup, zpool sdb5 |
| nucbackup (usb4t/backup/nuc) | | then restic instance leg -> S3 |
| 05:00 pull ks4:* -> ks4backup | | 05:00 restic: DB dumps + data |
| [pending FTTH] | | trees -> S3 (restic-data) |
| 05:30 apt upgrade all containers | | Sun 14:00 restic maintenance |
+-----------------------------------+ +-------------------------------------+
phones/laptops: WG peers 10.8.0.2-3 reach 192.168.1.x through the same endpoint
```
Both tunnels initiate **from** nuc (home NAT, dynamic IP) toward ks4's
fixed endpoint; ks4's incus API is never exposed to the internet.
### Conventions
- One markdown file per topic in the correct subdir, containing the full
implementation notes, configuration, and troubleshooting notes.
- Containers are built from Debian/Ubuntu images and configured
exclusively through `incus exec`/`incus config` so the doc is the
single source of truth — rebuilding = re-running the script.
- Adding a service to ks4: follow
[new-container.md](new-container.md) (no Docker in containers —
incus runs OCI images natively and `incus-compose` handles stacks;
data paths go into `scripts/restic-paths`).