Quick Commands

# edit + deploy
git status
git add -A
git commit -m "docs: update"
git push

# rebuild static blog output (local)
cd site
npm ci --no-audit --no-fund
npm run build

# VPS: pull only
# (on server)
git pull --ff-only

Podman Global Configuration

awesome — here’s a clean, English, production-style doc you can drop into your repo/Wiki. It explains why we pick these settings and gives you the exact configs + commands. I kept it pragmatic and battle-tested for Ubuntu + rootless Podman with one UNIX user per app/pod, and your Nginx/Vault sidecar pattern.


Global Rootless Podman + TLS Sidecar: Reference Configuration

Why this design (executive summary)

  • Rootless per app/user = strong isolation.
    Each app runs under its own UNIX user → separate namespaces, files, tokens, systemd units. A compromise stays local.
  • Podman with **crun** and **netavark** = modern, fast, reliable.
    crun is the default OCI runtime for rootless (lower overhead than runc).
    netavark + aardvark-dns replace legacy CNI, avoid missing plugin issues, and work great without root.
  • No **network_mode: host** in rootless.
    Rootless cannot bind host network safely → we use explicit **ports** mappings and make the container listen on 0.0.0.0:<port>.
  • Vault Agent per app-user issues and rotates internal TLS (*.int.privsec.ch).
    Edge (proxymain) terminates public TLS, then verifies upstream TLS by hostname + pinned CA on proxy layers.
  • Least privilege everywhere.
    Each app has its own PKI role, its own AppRole, its own cert/key directory, and its own agent/systemd unit.

1) System-wide packages (Ubuntu)

sudo apt update
sudo apt install -y \
  podman crun uidmap slirp4netns fuse-overlayfs \
  netavark aardvark-dns jq
# Only if you *must* keep legacy CNI (not recommended):
# sudo apt install -y containernetworking-plugins

Rationale

  • crun = optimized OCI runtime for rootless.
  • uidmap, slirp4netns, fuse-overlayfs = rootless fundamentals (user namespaces, unprivileged networking, overlay storage).
  • netavark/aardvark-dns = modern network stack for Podman 4+, replaces CNI in rootless.

2) Global Podman configuration (for all users)

/etc/containers/containers.conf

[engine]
runtime = "crun"
events_logger = "journald"

[engine.runtimes]
crun = ["/usr/bin/crun", "/usr/local/bin/crun"]
runc = ["/usr/bin/runc", "/usr/local/sbin/runc", "/usr/sbin/runc"]

[network]
# Rootless default; avoids CNI plugin issues
network_backend = "netavark"

Rationale

  • Forces a known runtime path so “default OCI runtime not found” can’t happen after updates.
  • Picks netavark globally to prevent user-specific drift into CNI.

(Optional) /etc/containers/storage.conf

[storage]
driver = "overlay"

[storage.options]
mount_program = "/usr/bin/fuse-overlayfs"

Rationale
Ensures overlay storage works rootless without needing elevated privileges.

System-wide migrate (users re-read defaults on next login)

sudo podman system migrate || true


3) Rootless service accounts (so pods run without interactive login)

For every app user (e.g., proxytest, apptest, orders, …):

sudo loginctl enable-linger <user>
sudo systemctl start "user@$(id -u <user>).service" || true

Rationale
Creates /run/user/<UID> (XDG runtime dir), making rootless Podman functional for non-interactive services.
(You may also add export XDG_RUNTIME_DIR=/run/user/$(id -u) in ~/.profile as a safety net.)