#!/bin/bash # To be run by user trf to create the pod and container with # Traefik and to create the systemd service # Environment variables POD_NAME='traefik_pod' CTR_NAME='traefik_ctr' IMAGE='docker.io/library/traefik:v3.5.4' TRAEFIK_HOST_PORT='8080' DASH_HOST_PORT='8085' HOST_INGRESS_IP='10.8.0.6' HOST_LOCAL_IP='127.0.0.1' NET_OPTS='slirp4netns:allow_host_loopback=true,port_handler=slirp4netns' BIND_DIR="$HOME/.local/share/traefik" DYNAMIC_DIR="$BIND_DIR/dynamic" STATIC_CFG="$BIND_DIR/traefik.yml" USER_SYSTEMD_DIR="$HOME/.config/systemd/user" POD_UNIT_FILE="$USER_SYSTEMD_DIR/pod-${POD_NAME}.service" # Prepare directories mkdir -p "$BIND_DIR" "$DYNAMIC_DIR" "$USER_SYSTEMD_DIR" # Create pod if not yet existing if ! podman pod exists "$POD_NAME"; then podman pod create \ -n "$POD_NAME" \ --network "$NET_OPTS" \ -p ${HOST_INGRESS_IP}:${TRAEFIK_HOST_PORT}:${TRAEFIK_HOST_PORT} \ -p ${HOST_LOCAL_IP}:${DASH_HOST_PORT}:${DASH_HOST_PORT} echo "Pod '$POD_NAME' created (rc=$?)" else echo "Pod '$POD_NAME' already exists." fi # Traefik container # Remove old container podman rm -f "$CTR_NAME" # New container podman run -d --name "$CTR_NAME" --pod "$POD_NAME" \ -v "$STATIC_CFG":/etc/traefik/traefik.yml:ro \ -v "$DYNAMIC_DIR":/etc/traefik/dynamic:ro \ "$IMAGE" echo "Started $CTR_NAME container (rc=$?)" # Generate systemd service files cd "$USER_SYSTEMD_DIR" podman generate systemd --files --new --name "$POD_NAME" echo "Generated systemd service files (rc=$?)" # Inject WireGuard IP readiness check into pod-${POD_NAME}.service awk -v ip="$HOST_INGRESS_IP" ' BEGIN { inserted=0 } # Insert the readiness check immediately BEFORE the pod create ExecStartPre /^ExecStartPre=\/usr\/bin\/podman pod create/ && inserted==0 { # Wait up to ~60s for ip to show up on any interface (safer than assuming wg0) # Uses grep -F to avoid regex escaping issues with dots in the IP. print "ExecStartPre=/bin/sh -ceu \047for i in $(seq 1 30); do ip -4 addr show | grep -Fq \" " ip "/\" && exit 0; sleep 2; done; echo \"IP " ip " not up\" >&2; exit 1\047" inserted=1 } { print } ' "$POD_UNIT_FILE" > "${POD_UNIT_FILE}.tmp" mv "${POD_UNIT_FILE}.tmp" "$POD_UNIT_FILE" echo "Injected WG IP readiness check for ${HOST_INGRESS_IP} into pod unit" # Stop & remove live pod and containers podman pod stop --ignore --time 15 "$POD_NAME" podman pod rm -f --ignore "$POD_NAME" if podman pod exists "$POD_NAME"; then echo "ERROR: Pod $POD_NAME still exists." exit 1 else echo "Stopped & removed live pod $POD_NAME and containers" fi # Enable systemd services systemctl --user daemon-reload systemctl --user enable --now "pod-${POD_NAME}.service" echo "Enabled systemd service pod-${POD_NAME}.service (rc=$?)" echo "Status: systemctl --user status pod-${POD_NAME}.service" echo "View logs: journalctl --user -u pod-${POD_NAME}.service -f" systemctl --user enable --now "container-${CTR_NAME}.service" echo "Enabled systemd service container-${CTR_NAME}.service (rc=$?)" echo "Status: systemctl --user status container-${CTR_NAME}.service" echo "View logs: journalctl --user -u container-${CTR_NAME}.service -f"