Compare commits
8 Commits
a10bf366e6
...
8b55af2d06
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
8b55af2d06 | ||
|
|
e38c283825 | ||
|
|
2182b821f4 | ||
|
|
6437c78a94 | ||
|
|
c31fbf0833 | ||
|
|
84036653fe | ||
|
|
a862606df2 | ||
|
|
faa68bfe83 |
@@ -48,7 +48,7 @@ argument_specs:
|
||||
elements: dict
|
||||
options:
|
||||
type:
|
||||
description: Type of volume
|
||||
description: Type of mount
|
||||
type: str
|
||||
required: true
|
||||
choices:
|
||||
@@ -80,6 +80,28 @@ argument_specs:
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_device:
|
||||
description: >-
|
||||
The path of a device which is mounted for the volume.
|
||||
Only applicable if mount type is volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_type:
|
||||
description: >-
|
||||
The filesystem type of device as used by the mount commands -t option
|
||||
Only applicable if mount type is volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_mount_options:
|
||||
description: >-
|
||||
The mount options to use for a filesystem as used by the mount command -o option
|
||||
Only applicable if mount type is volume.
|
||||
type: list
|
||||
elements: str
|
||||
required: false
|
||||
default: []
|
||||
|
||||
container_publish_ports:
|
||||
description: "A list of published ports in docker format (<host listen address>:<host port>:<container port>)"
|
||||
|
||||
@@ -27,6 +27,9 @@
|
||||
volume_name: "{{ volume.source }}"
|
||||
volume_uid: "{{ volume.user | default('') }}"
|
||||
volume_gid: "{{ volume.group | default('') }}"
|
||||
volume_type: "{{ volume.volume_type | default('') }}"
|
||||
volume_device: "{{ volume.volume_device | default('') }}"
|
||||
volume_mount_options: "{{ volume.volume_mount_options | default([]) }}"
|
||||
loop: "{{ _container_volumes }}"
|
||||
loop_control:
|
||||
loop_var: volume
|
||||
|
||||
@@ -18,7 +18,7 @@ _container_mounts: >-
|
||||
{{
|
||||
container_mounts | selectattr('type', '!=', 'volume') +
|
||||
container_mounts | selectattr('type', '==', 'volume')
|
||||
| community.general.remove_keys(['user', 'group'])
|
||||
| community.general.keep_keys(['type', 'source', 'destination', 'readonly'])
|
||||
| zip(_container_volume_mount_sources) | map('combine')
|
||||
}}
|
||||
|
||||
@@ -53,6 +53,8 @@ _container_quadlet_unit_options: |
|
||||
{% for want in container_wants %}
|
||||
Wants={{ want }}
|
||||
{% endfor %}
|
||||
[Service]
|
||||
SuccessExitStatus=0 143
|
||||
_container_quadlet_auto_start_options: |
|
||||
[Service]
|
||||
Restart=always
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
---
|
||||
service_container_command: []
|
||||
|
||||
service_domains: []
|
||||
service_vhost_locations: []
|
||||
service_proxy_pass_host_header: true
|
||||
@@ -11,6 +13,8 @@ service_container_secrets: []
|
||||
service_container_env: {}
|
||||
|
||||
service_database_type: none
|
||||
service_database_secret_type: mount
|
||||
service_database_secret_target: "{{ service_database_type }}"
|
||||
service_postgres_image: docker.io/library/postgres
|
||||
service_redis: false
|
||||
|
||||
|
||||
@@ -8,6 +8,13 @@ argument_specs:
|
||||
type: str
|
||||
required: true
|
||||
|
||||
service_container_command:
|
||||
description: Command to start the service container with.
|
||||
type: list
|
||||
required: false
|
||||
default: []
|
||||
elements: str
|
||||
|
||||
service_domains:
|
||||
description: A list of domains which should be proxied to the main service container
|
||||
type: list
|
||||
@@ -77,7 +84,7 @@ argument_specs:
|
||||
elements: dict
|
||||
options:
|
||||
type:
|
||||
description: Type of volume
|
||||
description: Type of mount
|
||||
type: str
|
||||
required: true
|
||||
choices:
|
||||
@@ -112,6 +119,28 @@ argument_specs:
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_device:
|
||||
description: >-
|
||||
The path of a device which is mounted for the volume.
|
||||
Only applicable if mount type is volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_type:
|
||||
description: >-
|
||||
The filesystem type of device as used by the mount commands -t option
|
||||
Only applicable if mount type is volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_mount_options:
|
||||
description: >-
|
||||
The mount options to use for a filesystem as used by the mount command -o option
|
||||
Only applicable if mount type is volume.
|
||||
type: list
|
||||
elements: str
|
||||
required: false
|
||||
default: []
|
||||
service_container_secrets:
|
||||
description:
|
||||
- >
|
||||
@@ -177,11 +206,24 @@ argument_specs:
|
||||
The password will also be available as the
|
||||
service_podman_secrets['{{ service_name }}-{{ service_database_type }}'] variable.
|
||||
type: str
|
||||
required: false
|
||||
choices:
|
||||
- postgres
|
||||
- none
|
||||
required: false
|
||||
default: none
|
||||
service_database_secret_type:
|
||||
description: Secret type for database secret for service container
|
||||
type: str
|
||||
choices:
|
||||
- mount
|
||||
- env
|
||||
required: false
|
||||
default: mount
|
||||
service_database_secret_target:
|
||||
description: Secret target for database secret for service container.
|
||||
type: str
|
||||
required: false
|
||||
default: "{{ service_database_type }}"
|
||||
service_postgres_image:
|
||||
description: Postgresql image to use.
|
||||
type: str
|
||||
@@ -207,8 +249,8 @@ argument_specs:
|
||||
description:
|
||||
- List of additional containers for the service.
|
||||
- >
|
||||
Will inherit most options from main service container, except for publish_ports.
|
||||
All options can be overridden per-container.
|
||||
Will inherit most options from main service container. All options can be overridden
|
||||
per-container.
|
||||
type: list
|
||||
required: false
|
||||
default: []
|
||||
@@ -228,6 +270,12 @@ argument_specs:
|
||||
type: str
|
||||
required: false
|
||||
default: "{{ service_container_image }}"
|
||||
command:
|
||||
description: Command to start the container with.
|
||||
type: list
|
||||
required: false
|
||||
default: "[]"
|
||||
elements: str
|
||||
mounts:
|
||||
description: List of bind mounts or volumes to be mounted inside the main service container.
|
||||
type: list
|
||||
@@ -236,7 +284,7 @@ argument_specs:
|
||||
elements: dict
|
||||
options:
|
||||
type:
|
||||
description: Type of volume
|
||||
description: Type of mount
|
||||
type: str
|
||||
required: true
|
||||
choices:
|
||||
@@ -261,6 +309,28 @@ argument_specs:
|
||||
- Defaults to false for volume and bind, true for template
|
||||
type: bool
|
||||
required: false
|
||||
volume_device:
|
||||
description: >-
|
||||
The path of a device which is mounted for the volume.
|
||||
Only applicable if mount type is volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_type:
|
||||
description: >-
|
||||
The filesystem type of device as used by the mount commands -t option
|
||||
Only applicable if mount type is volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_mount_options:
|
||||
description: >-
|
||||
The mount options to use for a filesystem as used by the mount command -o option
|
||||
Only applicable if mount type is volume.
|
||||
type: list
|
||||
elements: str
|
||||
required: false
|
||||
default: []
|
||||
publish_ports:
|
||||
description: "A list of published ports in docker format (<host listen address>:<host port>:<container port>)"
|
||||
type: list
|
||||
|
||||
@@ -3,18 +3,60 @@
|
||||
ansible.builtin.include_role:
|
||||
name: container
|
||||
vars:
|
||||
container_name: "{{ container.name }}"
|
||||
container_image: "{{ container.image | default(service_container_image) }}"
|
||||
_service_additional_volume_mounts: "{{ _service_additional_container.mounts | selectattr('type', '==', 'volume') }}"
|
||||
_service_additional_template_mounts: "{{ _service_additional_container.mounts | selectattr('type', '==', 'template') }}"
|
||||
_service_additional_host_directory: "/srv/{{ service_name }}"
|
||||
|
||||
_service_additional_container_volume_mounts: >-
|
||||
{{
|
||||
_service_additional_volume_mounts |
|
||||
zip(
|
||||
_service_additional_volume_mounts |
|
||||
map(attribute='source') |
|
||||
map('regex_replace', '^', service_name ~ '-') |
|
||||
map('community.general.dict_kv', 'source')
|
||||
) |
|
||||
map('combine')
|
||||
}}
|
||||
_service_additional_container_bind_mounts: "{{ _service_additional_container.mounts | selectattr('type', '==', 'bind') }}"
|
||||
_service_additional_container_template_mounts: >-
|
||||
{{
|
||||
([{'readonly': true}] * _service_additional_template_mounts | length) |
|
||||
zip(
|
||||
_service_additional_template_mounts,
|
||||
_service_additional_template_mounts |
|
||||
map(attribute='source') |
|
||||
map('regex_replace', '\.j2$', '') |
|
||||
map('regex_replace', '^', _service_host_directory ~ '/mounts/') |
|
||||
map('community.general.dict_kv', 'source'),
|
||||
([{'type': 'bind'}] * _service_additional_template_mounts | length)
|
||||
) |
|
||||
map('combine')
|
||||
}}
|
||||
|
||||
_service_additional_container_mounts: >-
|
||||
{{
|
||||
_service_additional_container_volume_mounts +
|
||||
_service_additional_container_bind_mounts +
|
||||
_service_additional_container_template_mounts
|
||||
if _service_additional_container.mounts is defined
|
||||
else
|
||||
_service_container_mounts
|
||||
}}
|
||||
|
||||
container_name: "{{ _service_additional_container.name }}"
|
||||
container_image: "{{ _service_additional_container.image | default(service_container_image) }}"
|
||||
container_image_creds: "{{ service_container_image_creds }}"
|
||||
container_command: "{{ _service_additional_container.command | default([]) }}"
|
||||
container_user: "{{ service_container_user }}"
|
||||
container_mounts: "{{ container.mounts | default(_service_container_mounts) }}"
|
||||
container_publish_ports: "{{ container.publish_ports | default([]) }}"
|
||||
container_mounts: "{{ _service_additional_container_mounts }}"
|
||||
container_publish_ports: "{{ _service_additional_container.publish_ports | default([]) }}"
|
||||
container_networks: "{{ _service_container_networks }}"
|
||||
container_secrets: "{{ container.secrets | default(_service_container_secrets) }}"
|
||||
container_env: "{{ container.env | default(service_container_env) }}"
|
||||
container_secrets: "{{ _service_additional_container.secrets | default(_service_container_secrets) }}"
|
||||
container_env: "{{ _service_additional_container.env | default(service_container_env) }}"
|
||||
container_requires: "{{ _service_container_requires }}"
|
||||
container_wants: "{{ service_wants }}"
|
||||
container_auto_update: "{{ service_auto_update }}"
|
||||
loop: "{{ _service_additional_containers }}"
|
||||
loop_control:
|
||||
loop_var: container
|
||||
loop_var: _service_additional_container
|
||||
|
||||
@@ -2,10 +2,6 @@
|
||||
- name: Validate inputs
|
||||
ansible.builtin.import_tasks: validation.yaml
|
||||
|
||||
- name: Initialize variables
|
||||
ansible.builtin.set_fact:
|
||||
_service_container_mounts: []
|
||||
|
||||
- name: Database for {{ service_name }}
|
||||
ansible.builtin.include_tasks: database.yaml
|
||||
when: _service_setup_database
|
||||
@@ -18,9 +14,9 @@
|
||||
ansible.builtin.include_tasks: secrets.yaml
|
||||
when: _service_container_secrets | length > 0
|
||||
|
||||
- name: Mounts for {{ service_name }}
|
||||
ansible.builtin.include_tasks: mounts.yaml
|
||||
when: service_container_mounts | length > 0
|
||||
- name: Template mounts for {{ service_name }}
|
||||
ansible.builtin.include_tasks: templates.yaml
|
||||
when: _service_template_mounts | length > 0
|
||||
|
||||
- name: Additional containers for {{ service_name }}
|
||||
ansible.builtin.include_tasks: additional.yaml
|
||||
@@ -33,6 +29,7 @@
|
||||
container_name: "{{ service_name }}"
|
||||
container_image: "{{ service_container_image }}"
|
||||
container_image_creds: "{{ service_container_image_creds }}"
|
||||
container_command: "{{ service_container_command }}"
|
||||
container_user: "{{ service_container_user }}"
|
||||
container_mounts: "{{ _service_container_mounts }}"
|
||||
container_publish_ports: "{{ service_container_publish_ports }}"
|
||||
|
||||
@@ -1,32 +0,0 @@
|
||||
---
|
||||
- name: Set container named mounts
|
||||
ansible.builtin.set_fact:
|
||||
_service_container_mounts: >
|
||||
{{ _service_container_mounts +
|
||||
[mount | combine({'source': service_name + '-' + mount.source})] }}
|
||||
when: mount.type == 'volume'
|
||||
|
||||
- name: Set container named mounts
|
||||
ansible.builtin.set_fact:
|
||||
_service_container_mounts: "{{ _service_container_mounts + [mount] }}"
|
||||
when: mount.type == 'bind'
|
||||
|
||||
- name: Template mounts
|
||||
when: mount.type == 'template'
|
||||
block:
|
||||
- name: Set template host path
|
||||
ansible.builtin.set_fact:
|
||||
_service_template_host_path: "{{ _service_host_directory }}/mounts/{{ (mount.source | split('.'))[0:-1] | join('.') }}" # Strip .j2 extension
|
||||
|
||||
- name: Template files for template mounts
|
||||
ansible.builtin.template:
|
||||
src: "{{ mount.source }}"
|
||||
dest: "{{ _service_template_host_path }}"
|
||||
mode: "0644"
|
||||
notify: "Restart container service {{ service_name }}"
|
||||
|
||||
- name: Set container template mounts
|
||||
ansible.builtin.set_fact:
|
||||
_service_container_mounts: >
|
||||
{{ _service_container_mounts +
|
||||
[{'readonly': true} | combine(mount) | combine({'type': 'bind', 'source': _service_template_host_path})] }}
|
||||
@@ -1,21 +0,0 @@
|
||||
---
|
||||
- name: Create template mount directories under /srv
|
||||
when: _service_template_mounts | length > 0
|
||||
block:
|
||||
- name: Create directory {{ _service_host_directory }}
|
||||
ansible.builtin.file:
|
||||
path: "{{ _service_host_directory }}"
|
||||
state: directory
|
||||
mode: "0755"
|
||||
|
||||
- name: Create directory {{ _service_host_directory + '/mounts' }}
|
||||
ansible.builtin.file:
|
||||
path: "{{ _service_host_directory }}/mounts"
|
||||
state: directory
|
||||
mode: "0700"
|
||||
|
||||
- name: Set mount definitions for {{ service_name }}
|
||||
ansible.builtin.include_tasks: mount.yaml
|
||||
loop: "{{ service_container_mounts }}"
|
||||
loop_control:
|
||||
loop_var: mount
|
||||
20
roles/service/tasks/templates.yaml
Normal file
20
roles/service/tasks/templates.yaml
Normal file
@@ -0,0 +1,20 @@
|
||||
---
|
||||
- name: Create directory {{ _service_host_directory }}
|
||||
ansible.builtin.file:
|
||||
path: "{{ _service_host_directory }}"
|
||||
state: directory
|
||||
mode: "0755"
|
||||
|
||||
- name: Create directory {{ _service_host_directory + '/mounts' }}
|
||||
ansible.builtin.file:
|
||||
path: "{{ _service_host_directory }}/mounts"
|
||||
state: directory
|
||||
mode: "0700"
|
||||
|
||||
- name: Template files for template mounts
|
||||
ansible.builtin.template:
|
||||
src: "{{ item[0].source }}"
|
||||
dest: "{{ item[1].source }}"
|
||||
mode: "0644"
|
||||
notify: "Restart container service {{ service_name }}"
|
||||
loop: "{{ _service_template_mounts | zip(_service_container_template_mounts) }}"
|
||||
@@ -1,7 +1,42 @@
|
||||
---
|
||||
_service_template_mounts: "{{ service_container_mounts | selectattr('type', '==', 'template') | list }}"
|
||||
_service_volume_mounts: "{{ service_container_mounts | selectattr('type', '==', 'volume') }}"
|
||||
_service_template_mounts: "{{ service_container_mounts | selectattr('type', '==', 'template') }}"
|
||||
_service_host_directory: "/srv/{{ service_name }}"
|
||||
|
||||
_service_container_volume_mounts: >-
|
||||
{{
|
||||
_service_volume_mounts |
|
||||
zip(
|
||||
_service_volume_mounts |
|
||||
map(attribute='source') |
|
||||
map('regex_replace', '^', service_name ~ '-') |
|
||||
map('community.general.dict_kv', 'source')
|
||||
) |
|
||||
map('combine')
|
||||
}}
|
||||
_service_container_bind_mounts: "{{ service_container_mounts | selectattr('type', '==', 'bind') }}"
|
||||
_service_container_template_mounts: >-
|
||||
{{
|
||||
([{'readonly': true}] * _service_template_mounts | length) |
|
||||
zip(
|
||||
_service_template_mounts,
|
||||
_service_template_mounts |
|
||||
map(attribute='source') |
|
||||
map('regex_replace', '\.j2$', '') |
|
||||
map('regex_replace', '^', _service_host_directory ~ '/mounts/') |
|
||||
map('community.general.dict_kv', 'source'),
|
||||
([{'type': 'bind'}] * _service_template_mounts | length)
|
||||
) |
|
||||
map('combine')
|
||||
}}
|
||||
|
||||
_service_container_mounts: >-
|
||||
{{
|
||||
_service_container_volume_mounts +
|
||||
_service_container_bind_mounts +
|
||||
_service_container_template_mounts
|
||||
}}
|
||||
|
||||
_service_setup_database: "{{ service_database_type != 'none' }}"
|
||||
_service_database_name: "{{ service_name }}-{{ service_database_type }}"
|
||||
|
||||
@@ -20,7 +55,13 @@ _service_container_secrets: >-
|
||||
| map('community.general.dict_kv', 'name')
|
||||
)
|
||||
| map('combine')
|
||||
+ ([{'name': _service_database_name, 'target': service_database_type }] if _service_setup_database else [])
|
||||
+ (
|
||||
[{
|
||||
'name': _service_database_name,
|
||||
'type': service_database_secret_type,
|
||||
'target': service_database_secret_target
|
||||
}] if _service_setup_database else []
|
||||
)
|
||||
}}
|
||||
|
||||
_service_additional_containers: >-
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
# vim:ft=yaml
|
||||
# {{ ansible_managed }}
|
||||
|
||||
signing_key_path: /run/secrets/synapse-signing-key
|
||||
signing_key_path: /run/secrets/signing-key
|
||||
media_store_path: /data/media
|
||||
log_config: /data/log.yaml
|
||||
|
||||
|
||||
@@ -1,3 +1,6 @@
|
||||
---
|
||||
volume_uid: ""
|
||||
volume_gid: ""
|
||||
volume_type: ""
|
||||
volume_device: ""
|
||||
volume_mount_options: []
|
||||
|
||||
7
roles/volume/handlers/main.yaml
Normal file
7
roles/volume/handlers/main.yaml
Normal file
@@ -0,0 +1,7 @@
|
||||
---
|
||||
- name: "Restart volume service {{ volume_name }}"
|
||||
ansible.builtin.systemd_service:
|
||||
name: "{{ volume_name }}-volume.service"
|
||||
state: restarted
|
||||
daemon_reload: true
|
||||
ignore_errors: '{{ ansible_check_mode }}'
|
||||
@@ -17,3 +17,19 @@ argument_specs:
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_device:
|
||||
description: The path of a device which is mounted for the volume.
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_type:
|
||||
description: The filesystem type of device as used by the mount commands -t option
|
||||
type: str
|
||||
required: false
|
||||
default: ""
|
||||
volume_mount_options:
|
||||
description: The mount options to use for a filesystem as used by the mount command -o option
|
||||
type: list
|
||||
elements: str
|
||||
required: false
|
||||
default: []
|
||||
|
||||
@@ -5,7 +5,8 @@
|
||||
- name: Create container volume service {{ volume_name }}
|
||||
containers.podman.podman_volume:
|
||||
name: "{{ volume_name }}"
|
||||
options: "{{ volume_options }}"
|
||||
options: "{{ _volume_options }}"
|
||||
state: quadlet
|
||||
quadlet_file_mode: "0644"
|
||||
notify: Reload systemd daemon
|
||||
quadlet_options: "{{ _volume_quadlet_options }}"
|
||||
notify: Restart volume service {{ volume_name }}
|
||||
|
||||
@@ -1,6 +1,24 @@
|
||||
---
|
||||
volume_mount_options_incl_empty:
|
||||
_volume_mount_options_incl_empty:
|
||||
- "{{ 'uid=' ~ volume_uid if volume_uid | length > 0 else '' }}"
|
||||
- "{{ 'gid=' ~ volume_gid if volume_gid | length > 0 else '' }}"
|
||||
volume_mount_options: "{{ volume_mount_options_incl_empty | select('!=', '') | list }}"
|
||||
volume_options: "{{ ['o=' ~ volume_mount_options | join(',')] if volume_mount_options | length > 0 else [] }}"
|
||||
_volume_mount_options: >-
|
||||
{{
|
||||
_volume_mount_options_incl_empty
|
||||
| select('!=', '')
|
||||
+ volume_mount_options
|
||||
}}
|
||||
_volume_options: >-
|
||||
{{
|
||||
(['o=' ~ _volume_mount_options | join(',')] if _volume_mount_options | length > 0 else [])
|
||||
+ (['type=' ~ volume_type] if volume_type | length > 0 else [])
|
||||
+ (['device=' ~ volume_device] if volume_device | length > 0 else [])
|
||||
}}
|
||||
|
||||
_volume_device_quadlet_options: |
|
||||
[Service]
|
||||
ExecStartPost=/usr/bin/podman volume mount {{ volume_name }}
|
||||
ExecStop=/usr/bin/podman volume unmount {{ volume_name }}
|
||||
ExecStop=/usr/bin/podman volume rm {{ volume_name }}
|
||||
_volume_quadlet_options: >-
|
||||
{{ [_volume_device_quadlet_options] if volume_device | length > 0 else [] }}
|
||||
|
||||
Reference in New Issue
Block a user