Files
fpov-exchange/roles/trade_hub/tasks/main.yml
2026-11-13 13:01:22 -07:00

216 lines
7.2 KiB
YAML

---
- name: Check whether podman is installed
ansible.builtin.command: podman --version
register: trade_hub_podman_check
changed_when: false
failed_when: false
check_mode: false
- name: Install podman when requested
ansible.builtin.package:
name: podman
state: present
become: true
when:
- trade_hub_podman_check.rc != 0
- trade_hub_install_podman | bool
- name: Re-check podman after installation
ansible.builtin.command: podman --version
register: trade_hub_podman_recheck
changed_when: false
failed_when: false
check_mode: false
when: trade_hub_podman_check.rc != 0
- name: Require podman to be available
ansible.builtin.assert:
that:
- trade_hub_podman_check.rc == 0 or (trade_hub_podman_recheck.rc | default(1)) == 0
fail_msg: >-
podman is not installed on {{ inventory_hostname }}. Install it first
(for example with the "packages" role) or run this role with
-e trade_hub_install_podman=true.
- name: Remove the legacy Apache container when requested
containers.podman.podman_container:
name: "{{ trade_hub_legacy_apache_container }}"
state: absent
when: trade_hub_remove_legacy_apache | bool
- name: Create the application directory
ansible.builtin.file:
path: "{{ trade_hub_app_dir }}"
state: directory
mode: "0755"
- name: Stage the application build context
ansible.builtin.copy:
src: "{{ role_path }}/files/trade-hub/{{ item.src }}"
dest: "{{ trade_hub_app_dir }}/{{ item.dest }}"
mode: preserve
loop:
# Only the files needed by the two Dockerfiles are staged. Copying the
# whole tree would also ship local development artefacts such as .venv.
- { src: "backend/Dockerfile", dest: "backend/Dockerfile" }
- { src: "backend/requirements.txt", dest: "backend/requirements.txt" }
- { src: "backend/main.py", dest: "backend/main.py" }
- { src: "backend/app/", dest: "backend/app/" }
- { src: "backend/scripts/", dest: "backend/scripts/" }
- { src: "frontend/Dockerfile", dest: "frontend/Dockerfile" }
- { src: "frontend/nginx.conf", dest: "frontend/nginx.conf" }
- { src: "frontend/src/", dest: "frontend/src/" }
register: trade_hub_source
- name: Check whether the backend image exists
ansible.builtin.command:
argv:
- podman
- image
- exists
- "{{ trade_hub_backend_image }}:{{ trade_hub_image_tag }}"
register: trade_hub_backend_image_check
changed_when: false
failed_when: false
check_mode: false
- name: Check whether the frontend image exists
ansible.builtin.command:
argv:
- podman
- image
- exists
- "{{ trade_hub_frontend_image }}:{{ trade_hub_image_tag }}"
register: trade_hub_frontend_image_check
changed_when: false
failed_when: false
check_mode: false
- name: Build the backend image
ansible.builtin.command:
argv:
- podman
- build
- --tag
- "{{ trade_hub_backend_image }}:{{ trade_hub_image_tag }}"
- "{{ trade_hub_app_dir }}/backend"
when:
- trade_hub_build_images | bool
- trade_hub_force_rebuild | bool or trade_hub_source.changed or trade_hub_backend_image_check.rc != 0
register: trade_hub_backend_build
- name: Build the frontend image
ansible.builtin.command:
argv:
- podman
- build
- --tag
- "{{ trade_hub_frontend_image }}:{{ trade_hub_image_tag }}"
- "{{ trade_hub_app_dir }}/frontend"
when:
- trade_hub_build_images | bool
- trade_hub_force_rebuild | bool or trade_hub_source.changed or trade_hub_frontend_image_check.rc != 0
register: trade_hub_frontend_build
- name: Require prebuilt images when image builds are disabled
ansible.builtin.assert:
that:
- trade_hub_backend_image_check.rc == 0
- trade_hub_frontend_image_check.rc == 0
fail_msg: >-
trade_hub_build_images is false but {{ trade_hub_backend_image }}:{{
trade_hub_image_tag }} and/or {{ trade_hub_frontend_image }}:{{
trade_hub_image_tag }} are missing on {{ inventory_hostname }}.
when: not trade_hub_build_images | bool
- name: Record whether the application containers need to be recreated
ansible.builtin.set_fact:
trade_hub_recreate_containers: >-
{{ (trade_hub_force_rebuild | bool)
or ((trade_hub_build_images | bool) and (trade_hub_source.changed | default(false)))
or (trade_hub_backend_build.changed | default(false))
or (trade_hub_frontend_build.changed | default(false)) }}
- name: Ensure the PostgreSQL image is present
containers.podman.podman_image:
name: "{{ trade_hub_postgres_image }}"
state: present
when: not ansible_check_mode
- name: Create the podman network
containers.podman.podman_network:
name: "{{ trade_hub_network }}"
state: present
- name: Create the PostgreSQL data volume
containers.podman.podman_volume:
name: "{{ trade_hub_volume }}"
state: present
- name: Run the PostgreSQL container
containers.podman.podman_container:
name: "{{ trade_hub_db_container }}"
image: "{{ trade_hub_postgres_image }}"
state: started
recreate: "{{ trade_hub_force_rebuild | bool }}"
network: "{{ trade_hub_network }}"
network_aliases:
- db
env:
POSTGRES_USER: "{{ trade_hub_postgres_user }}"
POSTGRES_PASSWORD: "{{ trade_hub_postgres_password }}"
POSTGRES_DB: "{{ trade_hub_postgres_db }}"
volumes:
- "{{ trade_hub_volume }}:/var/lib/postgresql/data:Z"
restart_policy: unless-stopped
when: not ansible_check_mode
- name: Run the backend container
containers.podman.podman_container:
name: "{{ trade_hub_backend_container }}"
image: "{{ trade_hub_backend_image }}:{{ trade_hub_image_tag }}"
state: started
# podman does not recreate a container when its image tag resolves to a new
# ID, so recreate whenever the image was rebuilt or the app changed.
recreate: "{{ trade_hub_recreate_containers | bool }}"
network: "{{ trade_hub_network }}"
# The nginx upstream is http://backend:8000, so this alias must match.
network_aliases:
- backend
env:
DATABASE_URL: "{{ trade_hub_database_url }}"
DB_WAIT_SECONDS: "{{ trade_hub_db_wait_seconds }}"
COOKIE_SECURE: "{{ trade_hub_cookie_secure | bool | lower }}"
restart_policy: unless-stopped
when: not ansible_check_mode
- name: Run the frontend container
containers.podman.podman_container:
name: "{{ trade_hub_frontend_container }}"
image: "{{ trade_hub_frontend_image }}:{{ trade_hub_image_tag }}"
state: started
recreate: "{{ trade_hub_recreate_containers | bool }}"
network: "{{ trade_hub_network }}"
ports:
- "{{ trade_hub_frontend_bind }}:{{ trade_hub_frontend_port }}:80"
restart_policy: unless-stopped
when: not ansible_check_mode
- name: Enable podman-restart so containers survive a reboot
ansible.builtin.systemd:
name: podman-restart.service
enabled: true
state: started
when: trade_hub_enable_restart_service | bool
- name: Wait for the application to answer health checks
ansible.builtin.uri:
url: "{{ trade_hub_healthcheck_url }}"
status_code: 200
register: trade_hub_health
until: trade_hub_health.status == 200
retries: "{{ trade_hub_healthcheck_retries }}"
delay: "{{ trade_hub_healthcheck_delay }}"
changed_when: false
when: not ansible_check_mode