diff --git a/README.md b/README.md index c045368..259274c 100644 --- a/README.md +++ b/README.md @@ -1 +1 @@ -# Ansible Collection - snailed.ez_compose +# Ansible Collection - snailed.ez_docker diff --git a/galaxy.yml b/galaxy.yml index bcc3a2d..d66fbcb 100644 --- a/galaxy.yml +++ b/galaxy.yml @@ -1,6 +1,6 @@ namespace: snailed -name: ez_compose +name: ez_docker version: 1.0.0 @@ -15,18 +15,18 @@ license: - MIT tags: + - linux + - infrastructure - docker - - compose - - docker_compose dependencies: {} -repository: http://git.snaile.de/snailed/ez_compose +repository: http://git.snaile.de/snailed/ez_docker -documentation: http://git.snaile.de/snailed/ez_compose/src/branch/main/docs +documentation: http://git.snaile.de/snailed/ez_docker/src/branch/main/docs -homepage: http://git.snaile.de/snailed/ez_compose +homepage: http://git.snaile.de/snailed/ez_docker -issues: http://git.snaile.de/snailed/ez_compose/issues +issues: http://git.snaile.de/snailed/ez_docker/issues build_ignore: [] diff --git a/plugins/lookup/container_names.py b/plugins/lookup/container_names.py new file mode 100644 index 0000000..f6dd439 --- /dev/null +++ b/plugins/lookup/container_names.py @@ -0,0 +1,73 @@ +# Copyright: (c) 2025, Luca Bilke <luca@bil.ke> +# MIT License (see LICENSE) +# ruff: noqa: E402,ANN001,ANN003,ANN201 +# pyright: basic + +from __future__ import annotations + +DOCUMENTATION = """ +--- +name: container_names +version_added: 1.0.0 +short_description: Discover container names from ez_docker projects +description: + - This module is needed by ez_cp to find the names of containers to copy files into. + - It takes a project definition and returns a dict of name/container_name key/value pairs. +author: + - "Luca Bilke (@ssnailed)" +options: + _terms: + description: + - "name: definition dict of project to search in" + type: list + elements: dict + required: true +""" + +EXAMPLES = """ +- name: Discover container names in projects + ansible.builtin.set_fact: + containers: "{{ lookup('snailed.ez_docker.container_names', ez_docker_projects) }}" +""" + +RETURN = """ +_list: + description: + - List of discovered services in items format + - [{key: name, value: container_name}, ...] + type: list +""" + +from ansible.plugins.lookup import LookupBase + + +class LookupModule(LookupBase): + def run(self, terms, variables=None, **kwargs): + self.set_options(var_options=variables, direct=kwargs) + + ret = [] + for term in terms: + project_name = term.key + project = term.value + + for service_name, service in project.items(): + if not (overwrite := service.get("overwrite")): + overwrite = service.get("definition") + + if overwrite and (container_name := overwrite.get("container_name")): + ret.append( + { + "key": service_name, + "value": container_name, + } + ) + continue + + ret.append( + { + "key": service_name, + "value": f"{project_name}_{service_name}", + } + ) + + return ret diff --git a/plugins/lookup/slurp.py b/plugins/lookup/slurp.py new file mode 100644 index 0000000..c9a60ca --- /dev/null +++ b/plugins/lookup/slurp.py @@ -0,0 +1,74 @@ +# Copyright: (c) 2025, Luca Bilke <luca@bil.ke> +# MIT License (see LICENSE) +# ruff: noqa: E402,ANN001,ANN003,ANN201 +# pyright: basic + +from __future__ import annotations + +DOCUMENTATION = """ +--- +module: slurp +version_added: 1.0.0 +short_description: Lookup version of the slurp module +description: + - Instead of running the slurp module against local host, I wrote this module +author: + - "Luca Bilke (@ssnailed)" +options: + _terms: + description: path(s) of files to read + required: True +seealso: + - ref: playbook_task_paths + description: Search paths used for relative files. +""" + +EXAMPLES = """ +- ansible.builtin.debug: + msg: "{{ lookup('snailed.ez_docker.slurp', '/etc/foo.txt') | b64decode }}" +""" + +RETURN = """ + _list: + description: + - content of file(s) + type: list + elements: str +""" + +import base64 + +from ansible.errors import AnsibleError, AnsibleLookupError, AnsibleOptionsError +from ansible.plugins.lookup import LookupBase +from ansible.utils.display import Display + +display = Display() + + +class LookupModule(LookupBase): + def run(self, terms, variables=None, **kwargs): + ret = [] + self.set_options(var_options=variables, direct=kwargs) + + for term in terms: + display.debug(f"File lookup term: {term}") + + try: + lookupfile = self.find_file_in_search_path( + variables, "files", term, ignore_missing=True, + ) + display.vvvv(f"File lookup using {lookupfile} as file") + + if lookupfile: + b_contents, _ = self._loader._get_file_contents(lookupfile) # noqa: SLF001 # pyright: ignore[reportOptionalMemberAccess] + contents = base64.b64encode(b_contents) + ret.append(contents) + else: + msg = "file not found, use -vvvvv to see paths searched" + raise AnsibleOptionsError(msg) + + except AnsibleError as e: + msg = f"The 'file' lookup had an issue accessing the file '{term}'" + raise AnsibleLookupError(msg, orig_exc=e) # noqa: B904 + + return ret diff --git a/plugins/module_utils/common.py b/plugins/module_utils/common.py index 0d4acb6..d4c8d28 100644 --- a/plugins/module_utils/common.py +++ b/plugins/module_utils/common.py @@ -9,7 +9,7 @@ from pathlib import Path from typing import TYPE_CHECKING, Any, cast import yaml -from ansible_collections.snailed.ez_compose.plugins.module_utils.models import Result, State +from ansible_collections.snailed.ez_docker.plugins.module_utils.models import Result, State if TYPE_CHECKING: from ansible.module_utils.basic import AnsibleModule # pyright: ignore[reportMissingTypeStubs] diff --git a/plugins/module_utils/label/common.py b/plugins/module_utils/label/common.py index f67f3e3..36532e4 100644 --- a/plugins/module_utils/label/common.py +++ b/plugins/module_utils/label/common.py @@ -5,13 +5,13 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any, Callable -from ansible_collections.snailed.ez_compose.plugins.module_utils.common import ( +from ansible_collections.snailed.ez_docker.plugins.module_utils.common import ( clean_none, recursive_update, ) if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State BASE_ARGS: dict[str, Any] = {} diff --git a/plugins/module_utils/label/docker_volume_backupper.py b/plugins/module_utils/label/docker_volume_backupper.py index 549fa5b..b8575d5 100644 --- a/plugins/module_utils/label/docker_volume_backupper.py +++ b/plugins/module_utils/label/docker_volume_backupper.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "stop": {"type": "bool", "default": True}, diff --git a/plugins/module_utils/label/traefik_middleware.py b/plugins/module_utils/label/traefik_middleware.py index 248c7f4..2d614cf 100644 --- a/plugins/module_utils/label/traefik_middleware.py +++ b/plugins/module_utils/label/traefik_middleware.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "proxy_type": {"type": "str", "default": "http"}, diff --git a/plugins/module_utils/label/traefik_router.py b/plugins/module_utils/label/traefik_router.py index 9de64c8..5d83a18 100644 --- a/plugins/module_utils/label/traefik_router.py +++ b/plugins/module_utils/label/traefik_router.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "name": {"type": "str"}, diff --git a/plugins/module_utils/label/traefik_service.py b/plugins/module_utils/label/traefik_service.py index 110a611..7355015 100644 --- a/plugins/module_utils/label/traefik_service.py +++ b/plugins/module_utils/label/traefik_service.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "proxy_type": {"type": "str", "default": "http"}, diff --git a/plugins/module_utils/service/common.py b/plugins/module_utils/service/common.py index 8d224fc..4038c7c 100644 --- a/plugins/module_utils/service/common.py +++ b/plugins/module_utils/service/common.py @@ -7,13 +7,13 @@ import copy from dataclasses import replace from typing import TYPE_CHECKING, Any, Callable -from ansible_collections.snailed.ez_compose.plugins.module_utils.common import ( +from ansible_collections.snailed.ez_docker.plugins.module_utils.common import ( clean_none, recursive_update, ) if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State BASE_ARGS: dict[str, Any] = { "name": {"type": "str"}, diff --git a/plugins/module_utils/service/custom.py b/plugins/module_utils/service/custom.py index 223db4f..7cc927b 100644 --- a/plugins/module_utils/service/custom.py +++ b/plugins/module_utils/service/custom.py @@ -5,11 +5,11 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any -from ansible_collections.snailed.ez_compose.plugins.module_utils import label, spec -from ansible_collections.snailed.ez_compose.plugins.module_utils.common import clean_none +from ansible_collections.snailed.ez_docker.plugins.module_utils import label, spec +from ansible_collections.snailed.ez_docker.plugins.module_utils.common import clean_none if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import ( + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import ( State, ) diff --git a/plugins/module_utils/service/docker_in_docker.py b/plugins/module_utils/service/docker_in_docker.py index 83ca103..f351cad 100644 --- a/plugins/module_utils/service/docker_in_docker.py +++ b/plugins/module_utils/service/docker_in_docker.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = {} diff --git a/plugins/module_utils/service/docker_socket_proxy.py b/plugins/module_utils/service/docker_socket_proxy.py index 22477a5..1f23ccc 100644 --- a/plugins/module_utils/service/docker_socket_proxy.py +++ b/plugins/module_utils/service/docker_socket_proxy.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "read_only": {"type": "bool", "default": True}, diff --git a/plugins/module_utils/service/docker_volume_backupper.py b/plugins/module_utils/service/docker_volume_backupper.py index 46735ff..4dc99c3 100644 --- a/plugins/module_utils/service/docker_volume_backupper.py +++ b/plugins/module_utils/service/docker_volume_backupper.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "archive": {"type": "path"}, diff --git a/plugins/module_utils/service/mariadb.py b/plugins/module_utils/service/mariadb.py index ddc32e9..eee0152 100644 --- a/plugins/module_utils/service/mariadb.py +++ b/plugins/module_utils/service/mariadb.py @@ -7,7 +7,7 @@ import shlex from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "backup": {"type": "bool", "default": True}, diff --git a/plugins/module_utils/service/postgres.py b/plugins/module_utils/service/postgres.py index b2d172f..1ef378c 100644 --- a/plugins/module_utils/service/postgres.py +++ b/plugins/module_utils/service/postgres.py @@ -7,7 +7,7 @@ import shlex from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = { "backup": {"type": "bool", "default": True}, diff --git a/plugins/module_utils/service/redis.py b/plugins/module_utils/service/redis.py index d5cdf57..b3f62bf 100644 --- a/plugins/module_utils/service/redis.py +++ b/plugins/module_utils/service/redis.py @@ -6,7 +6,7 @@ from __future__ import annotations from typing import TYPE_CHECKING, Any if TYPE_CHECKING: - from ansible_collections.snailed.ez_compose.plugins.module_utils.models import State + from ansible_collections.snailed.ez_docker.plugins.module_utils.models import State EXTRA_ARGS = {} diff --git a/plugins/module_utils/spec.py b/plugins/module_utils/spec.py index bec0861..106fee9 100644 --- a/plugins/module_utils/spec.py +++ b/plugins/module_utils/spec.py @@ -9,7 +9,7 @@ from typing import TYPE_CHECKING, Any if TYPE_CHECKING: from types import ModuleType -from ansible_collections.snailed.ez_compose.plugins.module_utils import ( +from ansible_collections.snailed.ez_docker.plugins.module_utils import ( label, service, ) diff --git a/plugins/modules/compose.py b/plugins/modules/compose.py index 921666e..9e6f76a 100755 --- a/plugins/modules/compose.py +++ b/plugins/modules/compose.py @@ -9,6 +9,7 @@ from dataclasses import asdict # TODO: break this down per module # TODO: generate this by reassembling +# TODO: add note about not setting container_name or host_name in defaults DOCUMENTATION = """ --- module: compose @@ -456,7 +457,7 @@ options: from importlib.util import find_spec from ansible.module_utils.basic import AnsibleModule # pyright: ignore[reportMissingTypeStubs] -from ansible_collections.snailed.ez_compose.plugins.module_utils import ( +from ansible_collections.snailed.ez_docker.plugins.module_utils import ( common, service, spec, @@ -473,7 +474,7 @@ def main() -> None: }, "project_dir": { "type": "path", - "default": "/var/lib/ez_compose", + "default": "/var/lib/ez_docker", }, "settings": spec.settings_spec(), "services": spec.service_argument_spec(), diff --git a/pyproject.toml b/pyproject.toml index 439f0c0..ff6629f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -14,18 +14,13 @@ ignore = [ "COM812", "D100", "D101", + "D102", "D103", "D104", "D203", "D213", ] -[tool.ruff.lint.per-file-ignores] -"tests/units/**" = [ - "S101", - "PT009", -] - [tool.ruff.format] line-ending = "lf" diff --git a/roles/compose/tasks/main.yml b/roles/compose/tasks/main.yml deleted file mode 100644 index c68a0b1..0000000 --- a/roles/compose/tasks/main.yml +++ /dev/null @@ -1,74 +0,0 @@ ---- -- name: Login in to registries - community.docker.docker_login: - registry_url: "{{ item.registry }}" - username: "{{ item.username }}" - password: "{{ item.password }}" - loop: "{{ compose_registry_logins }}" - no_log: true - when: >- - ez_compose_state | default(None) == "present" - and ez_compose_registry_logins is defined - and ez_compose_registry_logins - -- name: Ensure shared networks exist - community.docker.docker_network: - name: "{{ item.name }}" - attachable: "{{ item.attachable | default(omit) }}" - connected: "{{ item.connected | default(omit) }}" - driver: "{{ item.driver | default(omit) }}" - driver_options: "{{ item.driver_options | default(omit) }}" - enable_ipv6: "{{ item.enable_ipv6 | default(omit) }}" - force: "{{ item.force | default(omit) }}" - ipam_config: "{{ item.ipam_config | default(omit) }}" - ipam_driver: "{{ item.ipam_driver | default(omit) }}" - labels: "{{ item.labels | default(omit) }}" - scope: "{{ item.scope | default(omit) }}" - state: "{{ item.state | default(omit) }}" - loop: "{{ ez_compose_shared_networks }}" - when: >- - ez_compose_state | default(None) == "present" - and ez_compose_shared_networks is defined - and ez_compose_shared_networks - -- name: Ensure shared volumes exist - community.docker.docker_network: - name: "{{ item.name }}" - driver: "{{ item.driver | default(omit) }}" - driver_options: "{{ item.driver_options | default(omit) }}" - labels: "{{ item.labels | default(omit) }}" - recreate: "{{ item.recreate | default(omit) }}" - state: "{{ item.state | default(omit) }}" - loop: "{{ ez_compose_shared_volumes }}" - when: >- - ez_compose_state | default(None) == "present" - and ez_compose_shared_volumes is defined - and ez_compose_shared_volumes - -- name: Discover project definitions - ansible.builtin.set_fact: - ez_compose_projects: >- - {{ - hostvars[inventory_hostname] - | dict2items - | selectattr( - 'key', 'in', ( - hostvars[inventory_hostname].keys() - | select('match', '^ez_compose_project_') - ) - ) - }} - when: >- - ez_compose_projects is not defined - or not ez_compose_projects - -- name: Import project tasks - ansible.builtin.include_tasks: project.yml - when: >- - [project.key | split('_') | last, 'compose-all'] | intersect(ansible_run_tags) | length > 0 - and not - [project.key | split('_') | last, 'compose-all'] | intersect(ansible_skip_tags) | length > 0 - loop: "{{ ez_compose_projects }}" - loop_control: - loop_var: project - # no_log: true diff --git a/roles/compose/tasks/project.yml b/roles/compose/tasks/project.yml deleted file mode 100644 index b54279c..0000000 --- a/roles/compose/tasks/project.yml +++ /dev/null @@ -1,7 +0,0 @@ ---- -- name: "project | Write compose file: {{ project.name }}" - snailed.ez_compose.compose: - name: "{{ project.key | split('_') | last }}" - services: "{{ project.value }}" - settings: "{{ ez_compose_settings }}" - project_dir: "{{ ez_compose_project_dir }}" diff --git a/roles/ez_docker/default/main.yml b/roles/ez_docker/default/main.yml new file mode 100644 index 0000000..61ab360 --- /dev/null +++ b/roles/ez_docker/default/main.yml @@ -0,0 +1,49 @@ +--- +# Registries to log in to with community.docker.docker_login +ez_docker_registry_logins: [] +# - username: "example" +# password: "example" +# registry_url: "example.registry.url" + +# A list of docker compose network definitions to create with +# community.docker.docker_network and mark as external in projects +ez_docker_shared_networks: [] +# - name: "shared_network" + +# A list of docker compose volume definitions to create with +# community.docker.docker_volume and mark as external in projects +ez_docker_shared_volumes: [] +# - name: "shared_volume" + +# Directory to put compose projects into +ez_docker_project_dir: "/var/lib/ez_compose" + +# Settings for the module +ez_docker_settings: + default_definition: {} + # environment: + # TZ: "Europe/Berlin" + label_default_args: {} + # traefik_router: + # certresolver: "letsencrypt" + # entrypoints: ["web-secure"] + service_default_definitions: {} + # docker_volume_backupper: + # image: "offen/docker-volume-backup:v2.43.0" + # environment: + # BACKUP_CRON_EXPRESSION: "0 6 * * *" + # BACKUP_RETENTION_DAYS: "7" + service_default_args: {} + # docker_volume_backupper: + # archive: "/tank/docker-backups" +# +ez_cp_controller_files_root: "{{ playbook_dir }}/files/ez_cp/{{ inventory_hostname }}" +ez_cp_controller_templates_root: "{{ playbook_dir }}/templates/ez_cp/{{ inventory_hostname }}" + +# To copy into a non-running container we need the UID/GID for the files +# TODO: implement this +ez_cp_service_owners: {} +# project_name: +# service_name: +# uid: 1000 +# gid: 1000 diff --git a/roles/ez_docker/tasks/main.yml b/roles/ez_docker/tasks/main.yml new file mode 100644 index 0000000..d91396e --- /dev/null +++ b/roles/ez_docker/tasks/main.yml @@ -0,0 +1,38 @@ +--- +- name: Discover project definitions + ansible.builtin.set_fact: + ez_docker_projects: >- + {{ + hostvars[inventory_hostname] + | dict2items + | selectattr( + 'key', 'in', ( + hostvars[inventory_hostname].keys() + | select('match', '^ez_docker_project_') + ) + ) + }} + when: not ez_docker_projects + +- name: Login in to registries + community.docker.docker_login: "{{ item }}" # noqa: args[module] + loop: "{{ ez_docker_registry_logins }}" + no_log: true + when: ez_docker_registry_logins + +- name: Ensure shared networks exist # noqa: args[module] + community.docker.docker_network: "{{ item }}" + loop: "{{ ez_docker_shared_networks }}" + when: ez_docker_shared_networks + +- name: Ensure shared volumes exist # noqa: args[module] + community.docker.docker_volume: "{{ item }}" + loop: "{{ ez_docker_shared_volumes }}" + when: ez_docker_shared_volumes + +- name: Import per-project tasks + ansible.builtin.include_tasks: project.yml + loop: "{{ ez_docker_projects }}" + loop_control: + loop_var: project_definition + no_log: true diff --git a/roles/ez_docker/tasks/project.yml b/roles/ez_docker/tasks/project.yml new file mode 100644 index 0000000..6f26362 --- /dev/null +++ b/roles/ez_docker/tasks/project.yml @@ -0,0 +1,27 @@ +--- +- name: "project | Write compose files: {{ project_definition.key }}" + snailed.ez_docker.compose: + name: "{{ project_definition.key | split('_') | last }}" + services: "{{ project_definition.value }}" + settings: "{{ ez_docker_settings }}" + project_dir: "{{ ez_docker_project_dir }}" + no_log: true + +- name: "project | Start project: {{ project.name }}" + community.docker.docker_compose_v2: + pull: missing + project_src: "{{ ez_docker_project_dir }}/{{ project_definition.key }}" + state: "present" + +- name: "project | Import per-service tasks: {{ project_definition.key }}" + ansible.builtin.include_tasks: service.yml + with_snailed.ez_docker.container_names: "{{ project_definition }}" + loop_control: + loop_var: service + +- name: "project | Restart docker projects: {{ project_definition.key }}" + community.docker.docker_compose_v2: + services: services_changed + project_src: "{{ ez_docker_project_dir }}/{{ project_definition.key }}" + state: "restarted" + when: services_changed diff --git a/roles/ez_docker/tasks/service.yml b/roles/ez_docker/tasks/service.yml new file mode 100644 index 0000000..ae15f25 --- /dev/null +++ b/roles/ez_docker/tasks/service.yml @@ -0,0 +1,34 @@ +--- +- name: "service | Copy files into container: {{ service.key }}" + community.docker.docker_container_copy_into: + container: "{{ service.value }}" + container_path: "/{{ item.path }}" + content: >- + {{ snailed.ez_docker.slurp( + ez_cp_controller_files_root ~ "/" ~ project.key ~ "/" ~ service.key ~ "/" ~ item.path + ) }} + content_is_b64: true + mode: "{{ item.mode | int(base=8) }}" + when: item.state == "file" + with_community.general.filetree: + - "{{ ez_cp_controller_files_root }}/{{ project.key }}/{{ service.key }}" + register: copy + +- name: "service | Template files into container: {{ service.key }}" + community.docker.docker_container_copy_into: + container: "{{ service.value }}" + container_path: "/{{ item.path }}" + content: >- + {{ ansible.builtin.template( + ez_cp_controller_templates_root ~ "/" ~ project.key ~ "/" ~ service.key ~ "/" ~ item.path, + convert_data=false + ) }} + mode: "{{ item.mode | int(base=8) }}" + when: item.state == "file" + with_community.general.filetree: + - "{{ ez_cp_controller_templates_root }}/{{ project.key }}/{{ service.key }}" + register: template + +- name: "service | Register file changes: {{ service.key }}" + ansible.builtin.set_fact: + services_changed: "{{ services_changed | default([]) + [service.key] }}" diff --git a/test.json b/test.json index c672db6..9388faf 100644 --- a/test.json +++ b/test.json @@ -23,7 +23,6 @@ "label_helpers": { "docker_volume_backupper": {}, "traefik_router": { - "entrypoints": ["web-secure"], "rule": "Host(`taskwarrior-sync.snailed.de`)" } }, @@ -44,7 +43,8 @@ }, "label_default_args": { "traefik_router": { - "certresolver": "letsencrypt" + "certresolver": "letsencrypt", + "entrypoints": ["web-secure"] } }, "service_default_args": {