semaphoreui / semaphore

Modern UI for Ansible, Terraform, OpenTofu, PowerShell and other DevOps tools.
https://semaphoreui.com
MIT License
10.43k stars 1.05k forks source link

Execute task-template within python-virtual environment or container #998

Open ccuz opened 2 years ago

ccuz commented 2 years ago

The task-template are run by https://github.com/ansible-semaphore/semaphore/blob/develop/services/tasks/runner.go that calls https://github.com/ansible-semaphore/semaphore/blob/develop/lib/AnsiblePlaybook.go which starts the ansible-playbook command into a sub-process.

We have some shortcomings with this simple effective execution:

One idea, would be always build a python venv (https://docs.python.org/3/library/venv.html) before running the task-template process, thus dependencies doesn't clashes.

Another would be to create a container (i.e. docker image) an run the ansible within the provided container image. This provides a solution for problem 2 and ensure no semaphore environment variable leeks into the ansible-playbook execution. Not sure if possible in go while keeping everything simple, maybe using https://www.redhat.com/sysadmin/podman-inside-container. This would match https://access.redhat.com/documentation/en-us/red_hat_ansible_automation_platform/2.1/html-single/red_hat_ansible_automation_platform_upgrade_and_migration_guide/index#upgrading-to-ees

Maybe, the more flexible would be to allow a '/etc/semaphore/playground-setup.sh' to be run just before the ansible-playbook command, controlled by semaphore admin. Thus one could spin a container and pass the 'ansible-playbook' command and argument to it or setup a python venv before each execution. Or just use git hooks https://schacon.github.io/git/githooks.html#_post_checkout to perform environment setup (i.e. patching collections or setting up python venv).

ccuz commented 2 years ago

I ended up creating a hooks/post-checkout and hooks/post-merge within the ansible git project:

#!/bin/bash
echo "Git repo hook: $0"

echo "Create a python venv"
python3 -m .venv myproject
source .venv/bin/activate
pip install -r pip-packages.txt

echo "Installing roles/requirements.yml"
ansible-galaxy role install -r roles/requirements.yml --force

echo "Installing collections/requirements.yml"
ansible-galaxy collection install -r collections/requirements.yml --force

echo "Patching buggy collections"
git apply $(ls patches/*.patch)

In the dockerfile where semaphore is installed, I added: RUN git config --global core.hooksPath hooks Thus any ansible project getting checked-out by semaphore has the possibility to correctly setup the requirements and have clean dependencies not conflicting with other projects.

But the actual 'ansible-playbook' still doesn't run inside the virtual environment. It would need to run 'source myproject/bin/activate' just before actually running ansible-playbook.

ccuz commented 2 years ago

For the container runtime integration with podman: