Compare commits

..

9 Commits

Author SHA1 Message Date
uumas
db651723b2 Add pinp support and make windmill use it 2026-03-26 03:04:44 +02:00
uumas
1d180106d6 service: Use saner defaults for additional containers 2026-03-25 19:29:30 +02:00
uumas
9eaa306aa4 lint 2026-03-25 19:28:40 +02:00
uumas
f8e67b12d7 windmill: fix entrypoint script 2026-03-24 19:56:09 +02:00
uumas
5814267d66 Add windmill 2026-03-18 00:31:50 +02:00
uumas
defd2517ea service: Add postgres url to secrets 2026-03-18 00:30:25 +02:00
uumas
615c4013c1 Use caddy instead of socat for http proxying 2026-03-15 22:30:36 +02:00
uumas
77768e5483 small fixes 2026-03-15 22:30:16 +02:00
uumas
162972810f example: fix postgres examples 2026-03-15 21:56:16 +02:00
20 changed files with 501 additions and 56 deletions

View File

@@ -0,0 +1,4 @@
---
caddy_socket_proxy_target_container: "{{ caddy_socket_proxy_service_name }}"
caddy_socket_proxy_container_ip: ""
caddy_socket_proxy_auto_update: true

View File

@@ -0,0 +1,30 @@
---
argument_specs:
main:
description: >-
Sets up a caddy container and a systemd socket unit, forwarding traffic from it to
target container
options:
caddy_socket_proxy_service_name:
description: Name of the caddy service, used for systemd unit and container naming
type: str
required: true
caddy_socket_proxy_target_container:
description: Name of the container to forward traffic to
type: str
required: false
default: "{{ caddy_socket_proxy_service_name }}"
caddy_socket_proxy_target_http_port:
description: Port on the target container to forward traffic to
type: int
required: true
caddy_socket_proxy_container_ip:
description: IP address to assign to the caddy container.
type: str
required: false
default: ""
caddy_socket_proxy_auto_update:
description: Whether to automatically update the caddy container
type: bool
required: false
default: true

View File

@@ -0,0 +1,45 @@
---
- name: Create caddy socket proxy mount directories for {{ caddy_socket_proxy_service_name }}
ansible.builtin.file:
path: "{{ item.key }}"
state: directory
mode: "{{ item.value }}"
with_dict:
"/srv/{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy/": "0755"
"/srv/{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy/mounts": "0700"
"/srv/{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy/mounts/caddy": "0755"
- name: Configure caddy socket proxy for {{ caddy_socket_proxy_service_name }}
ansible.builtin.template:
src: Caddyfile.j2
dest: "/srv/{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy/mounts/caddy/Caddyfile"
mode: "0644"
notify: Restart container service {{ caddy_socket_proxy_service_name }}-caddy-socket-proxy
- name: Caddy socket proxy socket for {{ caddy_socket_proxy_service_name }}
ansible.builtin.import_role:
name: uumas.general.systemd_socket
vars:
systemd_socket_name: "{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy"
systemd_socket_requires:
- "{{ caddy_socket_proxy_target_container }}.service"
- name: Caddy container for {{ caddy_socket_proxy_service_name }}
ansible.builtin.import_role:
name: container
vars:
container_name: "{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy"
container_image: "docker.io/library/caddy:2-alpine"
container_mounts:
- type: bind
source: "/srv/{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy/mounts/caddy"
destination: /etc/caddy
readonly: true
container_networks:
- name: "{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy"
ip: "{{ caddy_socket_proxy_container_ip }}"
container_requires:
- "{{ caddy_socket_proxy_service_name }}-caddy-socket-proxy.socket"
- "{{ caddy_socket_proxy_target_container }}.service"
container_auto_start: false
container_auto_update: "{{ caddy_socket_proxy_auto_update }}"

View File

@@ -0,0 +1,12 @@
# {{ ansible_managed }}
{
servers {
trusted_proxies_unix
}
}
http:// {
bind fd/3
reverse_proxy {{ caddy_socket_proxy_service_name }}:{{ service_container_http_port }}
}
}

View File

@@ -19,7 +19,6 @@
service_container_http_port: 8080 service_container_http_port: 8080
service_domains: "{{ example_domains }}" service_domains: "{{ example_domains }}"
service_database_type: postgres service_database_type: postgres
service_postgres_tag: 16-alpine
service_container_publish_ports: service_container_publish_ports:
- "127.0.0.1:8080:8080" - "127.0.0.1:8080:8080"
- "0.0.0.0:4443:8043" - "0.0.0.0:4443:8043"
@@ -27,7 +26,7 @@
- network-online.target - network-online.target
service_container_env: service_container_env:
TZ: "Etc/UTC" TZ: "Etc/UTC"
DB_HOST: hello-world-db DB_HOST: postgres
DB_USER: hello-world DB_USER: hello-world
DB_PASSWORD__FILE: /run/secrets/postgres DB_PASSWORD__FILE: /run/secrets/postgres
service_additional_containers: service_additional_containers:

View File

@@ -10,7 +10,7 @@
opt: opt:
parent: "{{ ansible_facts.default_ipv4.interface if network_driver == 'macvlan' else omit }}" parent: "{{ ansible_facts.default_ipv4.interface if network_driver == 'macvlan' else omit }}"
quadlet_options: quadlet_options:
- | - |-
[Service] [Service]
ExecStopPost=/usr/bin/podman network rm {{ network_name }} ExecStopPost=/usr/bin/podman network rm {{ network_name }}
notify: notify:

View File

@@ -17,6 +17,7 @@ service_container_devices: []
service_container_secrets: [] service_container_secrets: []
service_container_env: {} service_container_env: {}
service_container_add_capabilities: [] service_container_add_capabilities: []
service_container_pinp: false
service_database_type: none service_database_type: none
service_database_additional_networks: [] service_database_additional_networks: []

View File

@@ -277,6 +277,22 @@ argument_specs:
default: [] default: []
elements: str elements: str
service_container_pinp:
description:
- If true, runs the container with podman in podman
- This starts a podman service inside the outer container
- The podman socket is exposed to the inner container at /var/run/docker.sock
- >-
This allows the container to manage other containers, which are run inside the
same outer container
- >-
The inner containers use host networking, so they share the network namespace
with the outer container and each other.
- This support is experimental and may not work with all images or configurations.
type: bool
required: false
default: false
service_database_type: service_database_type:
description: description:
- Database type to set up. - Database type to set up.
@@ -340,9 +356,10 @@ argument_specs:
service_additional_containers: service_additional_containers:
description: description:
- List of additional containers for the service. - List of additional containers for the service.
- > - >-
Will inherit most options from main service container. All options can be overridden If image is not specified, will use service container image and
per-container. inherit most options from main service container.
- All options can be overridden per-container.
type: list type: list
required: false required: false
default: [] default: []
@@ -363,26 +380,30 @@ argument_specs:
required: false required: false
default: "{{ service_container_image }}" default: "{{ service_container_image }}"
user: user:
description: The UID to run as inside the container description:
- The UID to run as inside the container.
- Defaults to <service_container_user> if same image, "" otherwise.
type: str type: str
required: false required: false
default: "{{ service_container_user }}"
command: command:
description: Command to start the container with. description:
- Command to start the container with.
- Defaults to <service_container_command> if same image, [] otherwise.
type: list type: list
required: false required: false
default: []
elements: str elements: str
entrypoint: entrypoint:
description: Entrypoint to use in the container description:
- Entrypoint to use in the container
- Defaults to <service_container_entrypoint> if same image, "" otherwise.
type: str type: str
required: false required: false
default: ""
mounts: mounts:
description: List of bind mounts or volumes to be mounted inside the container. description:
- List of bind mounts or volumes to be mounted inside the container.
- Defaults to <service_container_mounts> if same image, [] otherwise.
type: list type: list
required: false required: false
default: "{{ service_container_mounts }}"
elements: dict elements: dict
options: options:
type: type:
@@ -450,10 +471,11 @@ argument_specs:
required: false required: false
default: [] default: []
devices: devices:
description: List of devices to be added inside the container. description:
- List of devices to be added inside the container.
- Defaults to <service_container_devices> if same image, [] otherwise.
type: list type: list
required: false required: false
default: "{{ service_container_devices }}"
elements: dict elements: dict
options: options:
source: source:
@@ -506,15 +528,17 @@ argument_specs:
type: int type: int
required: false required: false
env: env:
description: A dict of environment variables for the container description:
- A dict of environment variables for the container
- Defaults to <service_container_env> if same image, {} otherwise.
type: dict type: dict
required: false required: false
default: "{{ service_container_env }}"
add_capabilities: add_capabilities:
description: List of capabilities to add to the container description:
- List of capabilities to add to the container
- Defaults to <service_container_add_capabilities> if same image, [] otherwise.
type: list type: list
required: false required: false
default: "{{ service_container_add_capabilities }}"
elements: str elements: str
secrets: secrets:
description: description:
@@ -525,9 +549,9 @@ argument_specs:
A dict of secrets and their values (including autogenerated values) is available as A dict of secrets and their values (including autogenerated values) is available as
`service_podman_secrets` for use in templates. This should only be used if the `service_podman_secrets` for use in templates. This should only be used if the
container doesn't support reading the secret from file or environment variable. container doesn't support reading the secret from file or environment variable.
- Defaults to <service_container_secrets> if same image, [] otherwise.
type: list type: list
required: false required: false
default: "{{ service_container_secrets }}"
elements: dict elements: dict
options: options:
name: name:
@@ -563,6 +587,21 @@ argument_specs:
the name of the environment variable. Defaults to secret name. the name of the environment variable. Defaults to secret name.
type: str type: str
required: false required: false
pinp:
description:
- If true, runs the container with podman in podman
- This starts a podman service inside the outer container
- The podman socket is exposed to the inner container at /var/run/docker.sock
- >-
This allows the container to manage other containers, which are run inside the
same outer container
- >-
The inner containers use host networking, so they share the network namespace
with the outer container and each other.
- This support is experimental and may not work with all images or configurations.
type: bool
required: false
default: false
service_requires: service_requires:
description: List of systemd units this service container depends on. description: List of systemd units this service container depends on.

View File

@@ -4,18 +4,18 @@
name: container name: container
vars: vars:
container_name: "{{ _service_additional_container.name }}" container_name: "{{ _service_additional_container.name }}"
container_image: "{{ _service_additional_container.image | default(service_container_image) }}" container_image: "{{ _service_additional_container_final.image }}"
container_command: "{{ _service_additional_container.command | default([]) }}" container_entrypoint: "{{ _service_additional_container_final.entrypoint }}"
container_entrypoint: "{{ _service_additional_container.entrypoint | default('') }}" container_command: "{{ _service_additional_container_final.command }}"
container_user: "{{ _service_additional_container.user | default(service_container_user) }}" container_user: "{{ _service_additional_container_final.user }}"
container_mounts: "{{ _service_additional_container_mounts }}" container_mounts: "{{ _service_additional_container_final.mounts }}"
container_devices: "{{ _service_additional_container.devices | default(service_container_devices) }}" container_devices: "{{ _service_additional_container.devices }}"
container_publish_ports: "{{ _service_additional_container_publish_ports }}" container_publish_ports: "{{ _service_additional_container_publish_ports }}"
container_networks: "{{ _service_additional_container_networks }}" container_networks: "{{ _service_additional_container_networks }}"
container_hostname: "{{ _service_additional_container.name | regex_replace('^' ~ service_name ~ '-', '') }}" container_hostname: "{{ _service_additional_container.name | regex_replace('^' ~ service_name ~ '-', '') }}"
container_secrets: "{{ _service_additional_container_secrets }}" container_secrets: "{{ _service_additional_container_secrets }}"
container_env: "{{ _service_additional_container.env | default(service_container_env) }}" container_env: "{{ _service_additional_container_final.env }}"
container_add_capabilities: "{{ _service_additional_container.add_capabilities | default(service_container_add_capabilities) }}" container_add_capabilities: "{{ _service_additional_container.add_capabilities }}"
container_requires: "{{ _service_container_requires }}" container_requires: "{{ _service_container_requires }}"
container_wants: "{{ _service_additional_container_wants }}" container_wants: "{{ _service_additional_container_wants }}"
container_auto_update: "{{ service_auto_update }}" container_auto_update: "{{ service_auto_update }}"

View File

@@ -34,3 +34,28 @@
directory_mode: "0755" directory_mode: "0755"
notify: Restart container service {{ service_name }} notify: Restart container service {{ service_name }}
loop: "{{ _service_all_copy_mounts | zip(_service_all_copy_mount_host_files) }}" loop: "{{ _service_all_copy_mounts | zip(_service_all_copy_mount_host_files) }}"
- name: Template entrypoint for pinp
ansible.builtin.template:
src: "pinp-entrypoint.sh.j2"
dest: "{{ _service_host_directory }}/mounts/pinp-entrypoint.sh"
mode: "0755"
vars:
pinp_inner_name: "{{ service_name }}"
pinp_inner_image: "{{ service_container_image }}"
pinp_inner_mounts: "{{ _service_container_pinp_inner_mounts }}"
pinp_inner_env: "{{ service_container_env }}"
when: service_container_pinp
- name: Template entrypoint for pinp of additional containers
ansible.builtin.template:
src: "pinp-entrypoint.sh.j2"
dest: "{{ _service_host_directory }}/mounts/{{ _service_additional_container.name }}-pinp-entrypoint.sh"
mode: "0755"
loop: "{{ _service_additional_containers | selectattr('pinp') }}"
loop_control:
loop_var: _service_additional_container
vars:
pinp_inner_name: "{{ _service_additional_container.name }}"
pinp_inner_image: "{{ _service_additional_container.image }}"
pinp_inner_mounts: "{{ _service_additional_container_pinp_inner_mounts }}"
pinp_inner_env: "{{ _service_additional_container.env }}"

View File

@@ -14,9 +14,12 @@
ansible.builtin.include_tasks: secrets.yaml ansible.builtin.include_tasks: secrets.yaml
when: _service_container_secrets | length > 0 when: _service_container_secrets | length > 0
- name: Template mounts for {{ service_name }} - name: Host mounts for {{ service_name }}
ansible.builtin.include_tasks: host_mounts.yaml ansible.builtin.include_tasks: host_mounts.yaml
when: (_service_all_template_mounts + _service_all_copy_mounts) | length > 0 when: >-
(_service_all_template_mounts + _service_all_copy_mounts) | length > 0
or service_container_pinp
or (_service_additional_containers | selectattr('pinp') | length > 0)
- name: Additional containers for {{ service_name }} - name: Additional containers for {{ service_name }}
ansible.builtin.include_tasks: additional.yaml ansible.builtin.include_tasks: additional.yaml
@@ -36,31 +39,31 @@
name: container name: container
vars: vars:
container_name: "{{ service_name }}" container_name: "{{ service_name }}"
container_image: "{{ service_container_image }}" container_image: "{{ _service_container.image }}"
container_command: "{{ service_container_command }}" container_entrypoint: "{{ _service_container.entrypoint }}"
container_entrypoint: "{{ service_container_entrypoint }}" container_command: "{{ _service_container.command }}"
container_user: "{{ service_container_user }}" container_user: "{{ _service_container.user }}"
container_mounts: "{{ _service_container_mounts }}" container_mounts: "{{ _service_container.mounts }}"
container_devices: "{{ service_container_devices }}" container_devices: "{{ service_container_devices }}"
container_publish_ports: "{{ _service_container_publish_ports }}" container_publish_ports: "{{ _service_container_publish_ports }}"
container_networks: "{{ _service_container_networks }}" container_networks: "{{ _service_container_networks }}"
container_secrets: "{{ _service_container_secrets }}" container_secrets: "{{ _service_container_secrets }}"
container_env: "{{ service_container_env }}" container_env: "{{ _service_container.env }}"
container_add_capabilities: "{{ service_container_add_capabilities }}" container_add_capabilities: "{{ service_container_add_capabilities }}"
container_requires: "{{ _service_container_requires }}" container_requires: "{{ _service_container_requires }}"
container_wants: "{{ _service_container_wants }}" container_wants: "{{ _service_container_wants }}"
container_auto_update: "{{ service_auto_update }}" container_auto_update: "{{ service_auto_update }}"
- name: Socat for http of {{ service_name }} - name: Caddy socket proxy for http of {{ service_name }}
ansible.builtin.include_role: ansible.builtin.include_role:
name: socat name: caddy_socket_proxy
when: service_container_http_port > 0 when: service_container_http_port > 0
vars: vars:
socat_service_name: "{{ service_name }}" caddy_socket_proxy_service_name: "{{ service_name }}"
socat_target_http_port: "{{ service_container_http_port }}" caddy_socket_proxy_target_http_port: "{{ service_container_http_port }}"
socat_container_ip: >- caddy_socket_proxy_container_ip: >-
{{ service_container_ip | ansible.utils.ipmath(257) if _service_static_ip else '' }} {{ service_container_ip | ansible.utils.ipmath(257) if _service_static_ip else '' }}
socat_auto_update: "{{ service_auto_update }}" caddy_socket_proxy_auto_update: "{{ service_auto_update }}"
- name: Socat for socket published ports of {{ service_name }} - name: Socat for socket published ports of {{ service_name }}
ansible.builtin.include_role: ansible.builtin.include_role:

View File

@@ -0,0 +1,26 @@
#!/bin/bash
# {{ ansible_managed }}
_term() {
echo "Received SIGTERM, stopping all containers"
kill "$child"
}
podman system service -t 0 &
podman run \
--rm \
-v /run/secrets:/run/secrets:ro \
{% for key, value in pinp_inner_env.items() %}
-e {{ key }}={{ value }} \
{% endfor %}
-v /tmp/storage-run-1000/podman/podman.sock:/var/run/docker.sock \
{% for mount in pinp_inner_mounts %}
--mount type={{ mount.type }},source={{ mount.source }},destination={{ mount.destination }}{% if mount.readonly | default(false) %},readonly{% endif %} \
{% endfor %}
--name {{ pinp_inner_name }} \
--network host \
{{ pinp_inner_image }} &
child=$!
trap _term SIGTERM
wait "$!"

View File

@@ -1,16 +1,77 @@
--- ---
_service_additional_containers_with_default_image: >-
{{
([{ 'image': service_container_image }] * service_additional_containers | length)
| zip(service_additional_containers)
| map('combine')
}}
_service_additional_container_same_image_defaults:
user: "{{ service_container_user }}"
command: "{{ service_container_command }}"
entrypoint: "{{ service_container_entrypoint }}"
devices: "{{ service_container_devices }}"
env: "{{ service_container_env }}"
add_capabilities: "{{ service_container_add_capabilities }}"
pinp: false
_service_additional_container_different_image_defaults:
user: ""
command: []
entrypoint: ""
mounts: []
devices: []
publish_ports: []
env: {}
add_capabilities: []
secrets: []
pinp: false
_service_additional_same_image_containers: >-
{{
_service_additional_containers_with_default_image
| selectattr('image', '==', service_container_image)
}}
_service_additional_different_image_containers: >-
{{
_service_additional_containers_with_default_image
| selectattr('image', '!=', service_container_image)
}}
_service_additional_containers: >- _service_additional_containers: >-
{{ {{
service_additional_containers (
| zip( (
service_additional_containers (
| map(attribute='name') [_service_additional_container_same_image_defaults] *
| map('regex_replace', '^', service_name ~ '-') (_service_additional_same_image_containers | length)
| map('community.general.dict_kv', 'name')
) )
| map('combine') | zip(_service_additional_same_image_containers)
| map('combine')
) +
(
(
[_service_additional_container_different_image_defaults] *
(_service_additional_different_image_containers | length)
)
| zip(_service_additional_different_image_containers)
| map('combine')
)
)
| zip(
(
_service_additional_same_image_containers +
_service_additional_different_image_containers
)
| map(attribute='name')
| map('regex_replace', '^', service_name ~ '-')
| map('community.general.dict_kv', 'name')
)
| map('combine')
}} }}
_service_additional_container_wants: >- _service_additional_container_wants: >-
{{ {{
service_wants service_wants
@@ -145,3 +206,59 @@ _service_additional_container_mounts: >-
else else
_service_container_mounts _service_container_mounts
}} }}
_service_additional_plain_container:
image: "{{ _service_additional_container.image }}"
entrypoint: "{{ _service_additional_container.entrypoint }}"
command: "{{ _service_additional_container.command }}"
user: "{{ _service_additional_container.user }}"
env: "{{ _service_additional_container.env }}"
mounts: "{{ _service_additional_container_mounts }}"
_service_additional_pinp_container_mounts:
- type: bind
source: "{{ _service_host_directory }}/mounts/{{ _service_additional_container.name }}-entrypoint.sh"
destination: /entrypoint.sh
readonly: true
- type: volume
source: "{{ _service_additional_container.name }}-containers"
destination: /home/podman/.local/share/containers
_service_additional_pinp_container:
image: quay.io/podman/stable:latest
entrypoint: /entrypoint.sh
command: []
user: podman
env: {}
mounts: >-
{{
_service_additional_pinp_container_mounts
+ (
_service_additional_container_mounts
| zip(
_service_additional_container_mounts
| map(attribute='source')
| map('replace', '/', '_')
| map('regex_replace', '^', '/mounts/')
| map('community.general.dict_kv', 'destination')
)
| map('combine')
)
}}
_service_additional_container_final: >-
{{ _service_additional_pinp_container if _service_additional_container.pinp else _service_additional_plain_container }}
_service_additional_container_pinp_inner_mounts: >-
{{
_service_additional_container_mounts
| zip(
_service_additional_container_mounts
| map(attribute='source')
| map('replace', '/', '_')
| map('regex_replace', '^', '/mounts/')
| map('community.general.dict_kv', 'source')
)
| map('combine')
}}

View File

@@ -7,13 +7,18 @@ _service_container_networks: >-
}] }]
+ ( + (
[{ [{
'name': service_name ~ '-socat', 'name': service_name ~ '-caddy-socket-proxy',
'ip': service_container_ip | ansible.utils.ipmath(256) if _service_static_ip else '' 'ip': service_container_ip | ansible.utils.ipmath(256) if _service_static_ip else ''
}] if service_container_http_port > 0 else [] }] if service_container_http_port > 0 else []
) )
+ ( + (
service_container_additional_networks service_container_additional_networks
+ (_service_container_publish_socket_ports | map(attribute='name') | map('regex_replace', '^', service_name ~ '-')) + (
_service_container_publish_socket_ports
| map(attribute='name')
| map('regex_replace', '^', service_name ~ '-')
| map('regex_replace', '$', '-socat')
)
) | map('community.general.dict_kv', 'name') ) | map('community.general.dict_kv', 'name')
}} }}
_service_static_ip: "{{ service_container_ip | length > 0 }}" _service_static_ip: "{{ service_container_ip | length > 0 }}"
@@ -28,8 +33,8 @@ _service_container_requires: >-
_service_container_wants: >- _service_container_wants: >-
{{ {{
service_wants service_wants
+ ([service_name + '-socat.socket'] if service_container_http_port > 0 else []) + ([service_name + '-caddy-socket-proxy.socket'] if service_container_http_port > 0 else [])
+ ([service_name + '-oauth2-proxy-socat.socket'] if _service_oauth2_proxy else []) + ([service_name + '-oauth2-proxy.socket'] if _service_oauth2_proxy else [])
+ _service_container_publish_socket_ports + _service_container_publish_socket_ports
| map(attribute='name') | map(attribute='name')
| map('regex_replace', '^', service_name ~ '-') | map('regex_replace', '^', service_name ~ '-')

View File

@@ -0,0 +1,55 @@
---
_service_plain_container:
image: "{{ service_container_image }}"
entrypoint: "{{ service_container_entrypoint }}"
command: "{{ service_container_command }}"
user: "{{ service_container_user }}"
env: "{{ service_container_env }}"
mounts: "{{ _service_container_mounts }}"
_service_pinp_container_mounts:
- type: bind
source: "{{ _service_host_directory }}/mounts/entrypoint.sh"
destination: /entrypoint.sh
readonly: true
- type: volume
source: "containers"
destination: /home/podman/.local/share/containers
_service_pinp_container:
image: quay.io/podman/stable:latest
entrypoint: /entrypoint.sh
command: []
user: podman
env: {}
mounts: >-
{{
_service_pinp_container_mounts
+ (
_service_container_mounts
| zip(
_service_container_mounts
| map(attribute='source')
| map('replace', '/', '_')
| map('regex_replace', '^', '/mounts/')
| map('community.general.dict_kv', 'destination')
)
| map('combine')
)
}}
_service_container: >-
{{ _service_pinp_container if service_container_pinp else _service_plain_container }}
_service_container_pinp_inner_mounts: >-
{{
_service_container_mounts
| zip(
_service_container_mounts
| map(attribute='source')
| map('replace', '/', '_')
| map('regex_replace', '^', '/mounts/')
| map('community.general.dict_kv', 'source')
)
| map('combine')
}}

View File

@@ -2,7 +2,7 @@
_service_native_socket: "{{ service_domains | length > 0 and service_container_http_port == 0 }}" _service_native_socket: "{{ service_domains | length > 0 and service_container_http_port == 0 }}"
_service_socket_path: >- _service_socket_path: >-
/run/{{ service_name ~ ('-socat' if not _service_native_socket else '' ) }}.sock /run/{{ service_name ~ ('-caddy-socket-proxy' if not _service_native_socket else '' ) }}.sock
_service_replacement_host_header: _service_replacement_host_header:
Host: "{{ service_name }}:{{ service_container_http_port }}" Host: "{{ service_name }}:{{ service_container_http_port }}"

View File

@@ -19,4 +19,17 @@ _service_container_secrets: >-
'target': service_database_secret_target 'target': service_database_secret_target
}] if _service_setup_database else [] }] if _service_setup_database else []
) )
+ (
[{
'name': _service_database_name ~ '-url',
'value':
'postgres://'
~ service_name | replace('-', '_')
~ ':' ~ service_podman_secrets[service_name ~ '-postgres']
~ '@postgres/' ~ service_name | replace('-', '_')
~ '?sslmode=disable',
'type': service_database_secret_type,
'target': service_database_secret_target ~ '-url'
}] if service_podman_secrets[service_name ~ '-postgres'] is defined else []
)
}} }}

View File

@@ -82,7 +82,7 @@
vhost_domains: vhost_domains:
- "{{ synapse_external_domain }}:8448" - "{{ synapse_external_domain }}:8448"
vhost_proxy_target_netproto: unix vhost_proxy_target_netproto: unix
vhost_proxy_target_socket: "/run/synapse-socat.sock" vhost_proxy_target_socket: "/run/synapse-caddy-socket-proxy.sock"
- name: Open port for synapse federation - name: Open port for synapse federation
ansible.posix.firewalld: ansible.posix.firewalld:

View File

@@ -0,0 +1,9 @@
---
argument_specs:
main:
description: Installs windmill with worker in podman in podman
options:
windmill_domain:
description: The domain to use for windmill
type: str
required: true

View File

@@ -0,0 +1,62 @@
---
- name: Windmill service
ansible.builtin.import_role:
name: service
vars:
service_name: windmill
service_container_image: ghcr.io/windmill-labs/windmill:main
service_container_mounts:
- type: volume
source: worker-logs
destination: /tmp/windmill/logs
service_container_http_port: 8000
service_domains:
- "{{ windmill_domain }}"
service_database_type: postgres
service_container_env:
DATABASE_URL_FILE: /run/secrets/postgres-url
MODE: server
service_additional_containers:
- name: worker
pinp: true
mounts:
- type: volume
source: worker-logs
destination: /tmp/windmill/logs
- type: volume
source: worker-dependency-cache
destination: /tmp/windmill/cache
env:
DATABASE_URL_FILE: /run/secrets/postgres-url
MODE: worker
WORKER_GROUP: default
ENABLE_UNSHARE_PID: "true"
UNSHARE_ISOLATION_FLAGS: "--user --map-root-user --pid --fork"
- name: worker-native
env:
DATABASE_URL_FILE: /run/secrets/postgres-url
MODE: worker
WORKER_TYPE: native
NATIVE_MODE: "true"
NUM_WORKERS: "8"
SLEEP_QUEUE: "200"
- name: lsp
image: ghcr.io/windmill-labs/windmill-extra:latest
secrets: []
mounts:
- type: volume
source: lsp-cache
destination: /puls/.cache
publish_ports:
- name: lsp
type: socket
container_port: 3001
env:
ENABLE_LSP: "true"
ENABLE_MULTIPLAYER: "false"
ENABLE_DEBUGGER: "false"
WINDMILL_BASE_URL: http://windmill:8000
service_vhost_locations:
- path: /ws/*
proxy_target_socket: /run/windmill-lsp-socat.sock