diff --git a/README.md b/README.md index e391d76..aeb4a61 100644 --- a/README.md +++ b/README.md @@ -29,6 +29,8 @@ Notes: - The default compose file uses traefik/whoami for smoke testing. - Edit each generated compose.yaml before production use. - App names must be lowercase slugs. +- If deploy reports XDG_RUNTIME_DIR missing, enable lingering for the runtime user: + `sudo loginctl enable-linger reudy` API service: - Nix now runs panel-api as a systemd service on 127.0.0.1:9911. diff --git a/panelctl.sh b/panelctl.sh index 9d046c0..61382eb 100644 --- a/panelctl.sh +++ b/panelctl.sh @@ -117,6 +117,49 @@ compose_command() { fail "no compose command available (need 'podman compose' or 'podman-compose')" } +ensure_podman_runtime_env() { + local uid + uid="$(id -u)" + + if [[ -z "${HOME:-}" ]]; then + HOME="$(getent passwd "${uid}" | cut -d: -f6 || true)" + export HOME + fi + + if [[ -z "${XDG_RUNTIME_DIR:-}" ]]; then + XDG_RUNTIME_DIR="/run/user/${uid}" + export XDG_RUNTIME_DIR + fi + + if [[ ! -d "${XDG_RUNTIME_DIR}" ]]; then + fail "XDG_RUNTIME_DIR '${XDG_RUNTIME_DIR}' does not exist for uid ${uid}. Ensure user runtime is available (e.g. loginctl enable-linger $(id -un))." + fi + + if [[ -z "${DBUS_SESSION_BUS_ADDRESS:-}" && -S "${XDG_RUNTIME_DIR}/bus" ]]; then + DBUS_SESSION_BUS_ADDRESS="unix:path=${XDG_RUNTIME_DIR}/bus" + export DBUS_SESSION_BUS_ADDRESS + fi + + # Avoid inherited docker/podman remote host env from external callers. + unset DOCKER_HOST + unset CONTAINER_HOST +} + +run_compose() { + local compose + compose="$(compose_command)" + + ensure_podman_runtime_env + + if [[ "${compose}" == *" compose" ]]; then + local podman_bin="${compose% compose}" + "${podman_bin}" compose "$@" + return + fi + + "${compose}" "$@" +} + write_default_compose() { local name="$1" local port="$2" @@ -239,11 +282,8 @@ cmd_deploy() { validate_name "${name}" load_app "${name}" - local compose - compose="$(compose_command)" - cmd_render_route "${name}" - ${compose} -f "${APP_COMPOSE_FILE}" up -d + run_compose -f "${APP_COMPOSE_FILE}" up -d maybe_reload_caddy echo "deployed app '${name}'" @@ -254,9 +294,7 @@ cmd_stop() { validate_name "${name}" load_app "${name}" - local compose - compose="$(compose_command)" - ${compose} -f "${APP_COMPOSE_FILE}" down + run_compose -f "${APP_COMPOSE_FILE}" down echo "stopped app '${name}'" } @@ -266,9 +304,7 @@ cmd_remove() { validate_name "${name}" load_app "${name}" - local compose - compose="$(compose_command)" - ${compose} -f "${APP_COMPOSE_FILE}" down || true + run_compose -f "${APP_COMPOSE_FILE}" down || true rm -f "${APP_ROUTE_FILE}" "$(app_manifest "${name}")" rm -rf "${APP_STACK_DIR}"