From 782deab95d879dc04e44cf74dda748e835a97dac Mon Sep 17 00:00:00 2001 From: Username Date: Tue, 17 Feb 2026 23:18:46 +0100 Subject: [PATCH] tools: rewrite ppf-deploy as playbook wrapper Replace sequential ansible ad-hoc calls with ansible-playbook. Add ansible_playbook_cmd to shared library. Supports --check for dry runs. --- tools/lib/ppf-common.sh | 11 ++++ tools/ppf-deploy | 142 +++++++++++++--------------------------- 2 files changed, 56 insertions(+), 97 deletions(-) diff --git a/tools/lib/ppf-common.sh b/tools/lib/ppf-common.sh index d85caed..bccfba0 100644 --- a/tools/lib/ppf-common.sh +++ b/tools/lib/ppf-common.sh @@ -108,6 +108,17 @@ ansible_cmd() { ) } +# Runs ansible-playbook with venv activated and ANSIBLE_REMOTE_TMP set. +# Usage: ansible_playbook_cmd +ansible_playbook_cmd() { + ( + # shellcheck disable=SC1090 + . "$ANSIBLE_VENV" + cd "$ANSIBLE_DIR" + ANSIBLE_REMOTE_TMP=/tmp/.ansible ansible-playbook "$@" + ) +} + # --------------------------------------------------------------------------- # Remote podman/compose wrappers # --------------------------------------------------------------------------- diff --git a/tools/ppf-deploy b/tools/ppf-deploy index 2952d04..5d342af 100755 --- a/tools/ppf-deploy +++ b/tools/ppf-deploy @@ -2,7 +2,7 @@ # ppf-deploy -- deploy PPF code to nodes # # Usage: -# ppf-deploy [--no-restart] [targets...] +# ppf-deploy [options] [targets...] # # Targets: # all odin + all workers (default) @@ -12,18 +12,22 @@ set -eu -SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)" +# Resolve to real path (handles symlinks from ~/.local/bin/) +SCRIPT_PATH="$(cd "$(dirname "$0")" && pwd)/$(basename "$0")" +SCRIPT_DIR="$(dirname "$(readlink -f "$SCRIPT_PATH")")" # shellcheck disable=SC1091 . "$SCRIPT_DIR/lib/ppf-common.sh" +PLAYBOOK_DIR="$SCRIPT_DIR/playbooks" + # --------------------------------------------------------------------------- # Usage # --------------------------------------------------------------------------- usage() { cat < ${dest}${C_RST}" - - ansible_cmd "$host" -m synchronize \ - -a "src=$PPF_DIR/ dest=$dest rsync_opts='--include=*.py,--include=servers.txt,--include=Dockerfile,--exclude=*'" \ - > /dev/null 2>&1 \ - && log_ok "$host synced" \ - || { log_err "$host sync failed"; continue; } -done - -# --------------------------------------------------------------------------- -# Step 3: Copy compose file per role -# --------------------------------------------------------------------------- -section "Copying compose files" - -for host in $HOSTS; do - if is_master "$host"; then - src="$PPF_DIR/compose.master.yml" - else - src="$PPF_DIR/compose.worker.yml" - fi - - ansible_cmd "$host" -m copy \ - -a "src=$src dest=/home/podman/ppf/compose.yml owner=podman group=podman" \ - > /dev/null 2>&1 \ - && log_ok "$host compose file" \ - || log_err "$host compose copy failed" -done - -# --------------------------------------------------------------------------- -# Step 4: Fix ownership -# --------------------------------------------------------------------------- -section "Fixing ownership" - -csv=$(hosts_csv $HOSTS) -ansible_cmd "$csv" -m raw -a "chown -R podman:podman /home/podman/ppf/" \ - > /dev/null 2>&1 \ - && log_ok "ownership fixed on all targets" \ - || log_err "ownership fix failed on some targets" - -# --------------------------------------------------------------------------- -# Step 5: Restart (unless --no-restart) -# --------------------------------------------------------------------------- -if [ "$DO_RESTART" -eq 1 ]; then - section "Restarting containers" - - for host in $HOSTS; do - compose_cmd "$host" "restart" > /dev/null 2>&1 \ - && log_ok "$host restarted" \ - || log_err "$host restart failed" - done - - # Brief pause for containers to settle - sleep 2 - - # --------------------------------------------------------------------------- - # Step 6: Show status - # --------------------------------------------------------------------------- - section "Container status" - - for host in $HOSTS; do - local_output=$(compose_cmd "$host" "ps" 2>/dev/null) || true - if echo "$local_output" | grep -qi "up\|running"; then - log_ok "$host" - else - log_warn "$host" - fi - echo "$local_output" | grep -v '^\s*$' | while IFS= read -r line; do - log_dim "$line" - done - done -else - log_info "Restart skipped (--no-restart)" +if [ "$DO_RESTART" -eq 0 ]; then + ARGS+=(-e "ppf_restart=false") fi -printf "\n" -log_ok "Deploy complete" +if [ "$CHECK_MODE" -eq 1 ]; then + ARGS+=(--check --diff) +fi + +[ -n "$VERBOSE" ] && ARGS+=("$VERBOSE") + +# Target resolution: map aliases to ansible --limit +case "$TARGETS" in + all) ;; # no --limit = all hosts in inventory + *) + LIMIT=$(resolve_targets $TARGETS | tr ' ' ',') + ARGS+=(--limit "$LIMIT") + ;; +esac + +ARGS+=("$PLAYBOOK_DIR/deploy.yml") + +# --------------------------------------------------------------------------- +# Run playbook +# --------------------------------------------------------------------------- +section "Deploying to ${TARGETS}" +ansible_playbook_cmd "${ARGS[@]}"