#!/usr/bin/env bash set -euo pipefail # =============================== # Load environment # =============================== ENV_FILE="./.env" if [[ ! -f "$ENV_FILE" ]]; then echo "ERROR: .env file not found. Copy .env.tmpl to .env and edit it." exit 1 fi # shellcheck disable=SC1090 source "$ENV_FILE" # =============================== # Validate required variables # =============================== : "${BACKUP_USER:?missing}" : "${PYTHON_BIN:?missing}" : "${BACKUP_INSTALL_DIR:?missing}" : "${BACKUP_RUNNER:?missing}" : "${WRAPPER_PATH:?missing}" RUNNER_PATH="$BACKUP_INSTALL_DIR/$BACKUP_RUNNER" HOME_DIR="/home/$BACKUP_USER" if [[ ! -x "$PYTHON_BIN" ]]; then echo "ERROR: Python binary not executable: $PYTHON_BIN" exit 1 fi if [[ ! -f "$RUNNER_PATH" ]]; then echo "ERROR: Runner not found: $RUNNER_PATH" exit 1 fi # =============================== # Create user (no shell) # =============================== if ! id "$BACKUP_USER" >/dev/null 2>&1; then useradd -m -d "$HOME_DIR" -s /usr/sbin/nologin "$BACKUP_USER" fi # =============================== # SSH setup # =============================== install -d -m 700 "$HOME_DIR/.ssh" touch "$HOME_DIR/.ssh/authorized_keys" chmod 600 "$HOME_DIR/.ssh/authorized_keys" chown -R "$BACKUP_USER:$BACKUP_USER" "$HOME_DIR/.ssh" # =============================== # Create root-owned wrapper # =============================== cat > "$WRAPPER_PATH" < "$SUDOERS_FILE" <" echo