From cf07ef7608aaaa0fce48c89856fd525028492cde Mon Sep 17 00:00:00 2001 From: "martin.fencl" Date: Mon, 24 Nov 2025 23:23:06 +0100 Subject: [PATCH] Add playbook to update Semaphore on VM via Proxmox --- update_semaphore.yml | 87 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 87 insertions(+) create mode 100644 update_semaphore.yml diff --git a/update_semaphore.yml b/update_semaphore.yml new file mode 100644 index 0000000..32d2437 --- /dev/null +++ b/update_semaphore.yml @@ -0,0 +1,87 @@ +# update_semaphore.yml + +- name: Update Semaphore on VM via Proxmox + hosts: proxmox + gather_facts: false + become: true + become_user: root + become_method: sudo + + vars: + # --- Connection to VM (provided by Semaphore env vars) --- + vm_ip: "{{ lookup('env', 'VM_IP') }}" # IP vm-portainer + vm_user: "{{ lookup('env', 'VM_USER') }}" + vm_pass: "{{ lookup('env', 'VM_PASS') }}" + use_sudo: false + + # --- Debug mode (controlled via Semaphore variable) --- + DEBUG: "{{ lookup('env', 'DEBUG') | default(0) | int }}" + + # --- Semaphore specifics --- + semaphore_project: "semaphore" + semaphore_compose_file: "/data/compose/semaphore/docker-compose.yml" + semaphore_service: "semaphore" + semaphore_image: "semaphoreui/semaphore:latest" + + # Docker command prefix (consistent behavior and quiet hints) + docker_prefix: "unalias docker 2>/dev/null || true; DOCKER_CLI_HINTS=0; command docker" + + # Commands to run on the target VM (quiet outputs) + # NOTE: This will likely kill the current Semaphore job when the container restarts. + semaphore_commands: + - "{{ docker_prefix }} pull -q {{ semaphore_image }} >/dev/null" + - "{{ docker_prefix }} compose -p {{ semaphore_project }} -f {{ semaphore_compose_file }} pull {{ semaphore_service }} >/dev/null" + - "{{ docker_prefix }} compose -p {{ semaphore_project }} -f {{ semaphore_compose_file }} up -d --no-deps --force-recreate {{ semaphore_service }} >/dev/null" + + tasks: + - name: Ensure sshpass is installed (for password-based SSH) # English comments + ansible.builtin.apt: + name: sshpass + state: present + update_cache: yes + + - name: Run Semaphore update commands on VM (via SSH) # use SSHPASS env, hide item value + ansible.builtin.command: + argv: + - sshpass + - -e # read password from SSHPASS environment + - ssh + - -o + - StrictHostKeyChecking=no + - -o + - ConnectTimeout=15 + - "{{ vm_user }}@{{ vm_ip }}" + - bash + - -lc + - "{{ ('sudo ' if use_sudo else '') + item }}" + environment: + SSHPASS: "{{ vm_pass }}" # supply password via environment + loop: "{{ semaphore_commands }}" + loop_control: + index_var: idx # capture loop index + label: "cmd-{{ idx }}" # avoid printing full command in (item=...) line + register: semaphore_cmds + changed_when: false + no_log: "{{ DEBUG == 0 }}" # hide outputs and env when not debugging + + - name: Show outputs for each Semaphore command + ansible.builtin.debug: + msg: | + CMD: {{ item.item }} + RC: {{ item.rc }} + STDOUT: + {{ (item.stdout | default('')).strip() }} + STDERR: + {{ (item.stderr | default('')).strip() }} + loop: "{{ semaphore_cmds.results }}" + when: DEBUG == 1 + + - name: Fail play if any Semaphore command failed # also hide item label + ansible.builtin.assert: + that: "item.rc == 0" + fail_msg: "Semaphore update failed on VM: {{ item.item }} (rc={{ item.rc }})" + success_msg: "All Semaphore update commands (pull/compose) succeeded." + loop: "{{ semaphore_cmds.results }}" + loop_control: + index_var: idx + label: "cmd-{{ idx }}"