From 8c9bdfbea5aed0fe97288c53ac21d408ce5417dc Mon Sep 17 00:00:00 2001 From: Bertrand Lanson Date: Sat, 9 Nov 2024 17:03:46 +0100 Subject: [PATCH] feat: enable customization of unit options in systemd file This also adjusts the unit.j2 template accordingly, as well as update documentation for the role. It also updates tests to cover more scenarios --- README.md | 101 ++++++++---------- defaults/main.yml | 4 +- molecule/default/group_vars/all.yml | 3 +- molecule/default_os/group_vars/all.yml | 3 +- molecule/with_custom_flags/group_vars/all.yml | 4 +- molecule/with_custom_flags/verify.yml | 2 +- .../with_custom_flags_os/group_vars/all.yml | 4 +- molecule/with_custom_flags_os/verify.yml | 2 +- templates/unit.j2 | 30 ++++-- vars/main.yml | 4 - 10 files changed, 81 insertions(+), 76 deletions(-) diff --git a/README.md b/README.md index f4e9fad..8d85492 100644 --- a/README.md +++ b/README.md @@ -1,20 +1,20 @@ -docker_systemd_service -========= -> This repository is only a mirror. Development and testing is done on a private gitea server. +**Docker systemd service** +========================= This role lets you configure a docker container and run it as a systemd service on **debian-based** distributions. This role is heavily sourced from [mhutter.docker-systemd-service](https://github.com/mhutter/ansible-docker-systemd-service), but aims at providing some of the missing features of said role. -Requirements ------------- +**Requirements** +--------------- -This roles assumes you have docker installed on the target host. You can use [ednz_cloud.install_docker](https://github.com/ednz_cloud/install_docker) to do so. +This roles assumes you have **docker** installed on the target host. You can use [ednz_cloud.install_docker](https://github.com/ednz_cloud/install_docker) to do so. -Role Variables --------------- -Available variables are listed below, along with default values. A sample file for the default values is available in `default/docker_systemd_service.yml.sample` in case you need it for any `group_vars` or `host_vars` configuration. +**Role Variables** +----------------- + +### Service configuration ```yaml -docker_systemd_service_container_name: "My-Service" # by default, set to "My-Service" +docker_systemd_service_container_name: "My-Service" ``` The name that will be assigned to the container. @@ -24,24 +24,47 @@ docker_systemd_service_image: # by default, not defined The image (and optionally tag) to use for the service. ```yaml -docker_systemd_service_container_env: {} # by default, set to {} +docker_systemd_service_start: true ``` -A list of key/value pairs, that will be written to the environment file for the container. the key NEEDS TO BE CAPTIALIZED, it will not be done automatically. Example: `MY_ENV_VAR: foobar`. +Indicates whether the service should start after installation. Defaults to `true`. ```yaml -docker_systemd_service_container_pull_image: true # by default, set to true +docker_systemd_service_systemd_unit_options: {} ``` -Whether or not the role should pull the image during its run. +Extra options to add to the `[Unit]` section of the systemd unit file. Map of strings. ```yaml -docker_systemd_service_container_pull_force_source: true # by default, set to true +docker_systemd_service_systemd_service_options: {} +``` +Extra options to add to the `[Service]` section of the systemd unit file. Map of strings. + +```yaml +docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" +``` +The name of the systemd service to register. + +### Container configuration + +```yaml +docker_systemd_service_container_env: {} +``` +A list of key/value pairs, that will be written to the environment file for the container. + +```yaml +docker_systemd_service_container_pull_image: true +``` +Whether or not the role should pull the image during its run, prior to starting the service. + +```yaml +docker_systemd_service_container_pull_force_source: true ``` If `docker_systemd_service_container_pull_image: true`, whether the pull you be executed at every run. See [`docker_image.force_source`](https://docs.ansible.com/ansible/latest/collections/community/docker/docker_image_module.html#parameter-force_source) ```yaml -docker_systemd_service_flags: [] # by default, set to [] +docker_systemd_service_flags: [] ``` This variable lets you pass whatever flags you need to the docker run command. It is a list, to which you can add multiple types of flags: + - ```yaml - key: value # will pass the flag --key "value" to the container. @@ -62,43 +85,13 @@ This variable lets you pass whatever flags you need to the docker run command. I - /path/on/host:/path/on/container - /var/run/docker.sock:/var/run/docker.sock:ro -```yaml -docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" # by default, set to "{{ docker_systemd_service_container_name }}_container" -``` -The name of the systemd service to register. - -```yaml -docker_systemd_service_systemd_options: [] # by default, set to [] -``` -Extra options to include in systemd service file. - -```yaml -docker_systemd_service_enabled: true # by default, set to true -``` -Whether the service should be enabled during the role's run. - -```yaml -docker_systemd_service_masked: false # by default, set to false -``` -Whether the service should be marked as masked. - -```yaml -docker_systemd_service_state: started # by default, set to started -``` -The state the service should be put in. Valid options are: `reloaded`, `restarted`, `started`, `stopped`, and `absent`. Realistically, you probably want to use `started` or `stopped`. `absent` can be used to remove the service and all associated files from the host. - -```yaml -docker_systemd_service_restart: true # by default, set to true -``` -Whether the role should restart the service if changes are made to any of the files (when service is already runing). - -Dependencies ------------- +**Dependencies** +--------------- None. -Example Playbook ----------------- +**Example Playbook** +------------------- ```yaml # calling the role inside a playbook with either the default or group_vars/host_vars @@ -107,12 +100,12 @@ Example Playbook - ednz_cloud.docker_systemd_service ``` -License -------- +**License** +---------- MIT / BSD -Author Information ------------------- +**Author Information** +--------------------- This role was created by Bertrand Lanson in 2023. diff --git a/defaults/main.yml b/defaults/main.yml index f5f55c1..9511e3c 100644 --- a/defaults/main.yml +++ b/defaults/main.yml @@ -8,6 +8,6 @@ docker_systemd_service_container_pull_force_source: true docker_systemd_service_flags: [] docker_systemd_service_container_cmd: [] docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" -docker_systemd_service_systemd_options: [] - +docker_systemd_service_systemd_unit_options: {} +docker_systemd_service_systemd_service_options: {} docker_systemd_service_start: true diff --git a/molecule/default/group_vars/all.yml b/molecule/default/group_vars/all.yml index 0c0e824..e362aa2 100644 --- a/molecule/default/group_vars/all.yml +++ b/molecule/default/group_vars/all.yml @@ -7,5 +7,6 @@ docker_systemd_service_container_pull_force_source: false docker_systemd_service_flags: [] docker_systemd_service_container_cmd: [] docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" -docker_systemd_service_systemd_options: [] +docker_systemd_service_systemd_unit_options: {} +docker_systemd_service_systemd_service_options: {} docker_systemd_service_start: false diff --git a/molecule/default_os/group_vars/all.yml b/molecule/default_os/group_vars/all.yml index 97cad22..30e1d9f 100644 --- a/molecule/default_os/group_vars/all.yml +++ b/molecule/default_os/group_vars/all.yml @@ -7,5 +7,6 @@ docker_systemd_service_container_pull_force_source: false docker_systemd_service_flags: [] docker_systemd_service_container_cmd: [] docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" -docker_systemd_service_systemd_options: [] +docker_systemd_service_systemd_unit_options: {} +docker_systemd_service_systemd_service_options: {} docker_systemd_service_start: true diff --git a/molecule/with_custom_flags/group_vars/all.yml b/molecule/with_custom_flags/group_vars/all.yml index 800a15e..8e9f314 100644 --- a/molecule/with_custom_flags/group_vars/all.yml +++ b/molecule/with_custom_flags/group_vars/all.yml @@ -12,5 +12,7 @@ docker_systemd_service_flags: - NET_ADMIN docker_systemd_service_container_cmd: [] docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" -docker_systemd_service_systemd_options: [] +docker_systemd_service_systemd_unit_options: + Requires: multi-user.target +docker_systemd_service_systemd_service_options: {} docker_systemd_service_start: false diff --git a/molecule/with_custom_flags/verify.yml b/molecule/with_custom_flags/verify.yml index 502939e..c3b4b56 100644 --- a/molecule/with_custom_flags/verify.yml +++ b/molecule/with_custom_flags/verify.yml @@ -49,9 +49,9 @@ nginx_expected_service_file: | # Ansible managed: Do NOT edit this file manually! [Unit] + Requires=multi-user.target After=docker.service PartOf=docker.service - Requires=docker.service [Service] EnvironmentFile=/etc/default/nginx diff --git a/molecule/with_custom_flags_os/group_vars/all.yml b/molecule/with_custom_flags_os/group_vars/all.yml index 6327d85..b6faddb 100644 --- a/molecule/with_custom_flags_os/group_vars/all.yml +++ b/molecule/with_custom_flags_os/group_vars/all.yml @@ -12,5 +12,7 @@ docker_systemd_service_flags: - NET_ADMIN docker_systemd_service_container_cmd: [] docker_systemd_service_name: "{{ docker_systemd_service_container_name }}_container" -docker_systemd_service_systemd_options: [] +docker_systemd_service_systemd_unit_options: + Requires: multi-user.target +docker_systemd_service_systemd_service_options: {} docker_systemd_service_start: true diff --git a/molecule/with_custom_flags_os/verify.yml b/molecule/with_custom_flags_os/verify.yml index 2d12e07..422aefc 100644 --- a/molecule/with_custom_flags_os/verify.yml +++ b/molecule/with_custom_flags_os/verify.yml @@ -49,9 +49,9 @@ nginx_expected_service_file: | # Ansible managed: Do NOT edit this file manually! [Unit] + Requires=multi-user.target After=docker.service PartOf=docker.service - Requires=docker.service [Service] EnvironmentFile=/etc/default/nginx diff --git a/templates/unit.j2 b/templates/unit.j2 index 3a0700c..3d7bb6b 100644 --- a/templates/unit.j2 +++ b/templates/unit.j2 @@ -1,21 +1,31 @@ # {{ ansible_managed }} -{% set service_systemd_options_keys = docker_systemd_service_systemd_options | selectattr("key") | map(attribute="key") | list %} +{% set service_systemd_service_options_keys = docker_systemd_service_systemd_service_options.keys() | list %} +{% set service_systemd_unit_options_keys = docker_systemd_service_systemd_unit_options.keys() | list %} [Unit] {% for key, value in docker_systemd_service_systemd_unit_options | dictsort %} {{ key }}={{ value }} {% endfor %} +{% if not 'After' in service_systemd_unit_options_keys %} +After=docker.service +{% endif %} +{% if not 'PartOf' in service_systemd_unit_options_keys %} +PartOf=docker.service +{% endif %} +{% if not 'Requires' in service_systemd_unit_options_keys %} +Requires=docker.service +{% endif %} [Service] -{% for item in docker_systemd_service_systemd_options %} -{{ item['key'] }}={{ item['value'] }} +{% for key, value in docker_systemd_service_systemd_service_options | dictsort %} +{{ key }}={{ value }} {% endfor %} -{% if not 'EnvironmentFile' in service_systemd_options_keys %} +{% if not 'EnvironmentFile' in service_systemd_service_options_keys %} EnvironmentFile={{ docker_systemd_service_sysconf_dir }}/{{ docker_systemd_service_container_name }} {% endif %} -{% if not 'ExecStartPre' in service_systemd_options_keys %} +{% if not 'ExecStartPre' in service_systemd_service_options_keys %} ExecStartPre=-{{ docker_systemd_service_docker_path }} rm -f {{ docker_systemd_service_container_name }} {% endif %} -{% if not 'ExecStart' in service_systemd_options_keys %} +{% if not 'ExecStart' in service_systemd_service_options_keys %} {% set docker_flags = docker_systemd_service_flags | create_docker_flags %} ExecStart={{ docker_systemd_service_docker_path }} run --name {{ docker_systemd_service_container_name }} \ --rm \ @@ -23,19 +33,19 @@ ExecStart={{ docker_systemd_service_docker_path }} run --name {{ docker_systemd_ {{ docker_flags -}}{% if docker_flags +%} {% endif %}{{ docker_systemd_service_image -}}{{ ' ' if docker_systemd_service_container_cmd else '' }}{% if docker_systemd_service_container_cmd is string %}{{ docker_systemd_service_container_cmd | trim }}{% else %}{{ docker_systemd_service_container_cmd | join(' ') | trim }}{% endif %} {% endif +%} -{% if not 'ExecStop' in service_systemd_options_keys %} +{% if not 'ExecStop' in service_systemd_service_options_keys %} ExecStop={{ docker_systemd_service_docker_path }} stop {{ docker_systemd_service_container_name }} {% endif %} {% if container_start_post is defined %} ExecStartPost=-{{ container_start_post }} {% endif %} -{% if not 'SyslogIdentifier' in service_systemd_options_keys %} +{% if not 'SyslogIdentifier' in service_systemd_service_options_keys %} SyslogIdentifier={{ docker_systemd_service_container_name }} {% endif %} -{% if not 'Restart' in service_systemd_options_keys %} +{% if not 'Restart' in service_systemd_service_options_keys %} Restart=always {% endif %} -{% if not 'RestartSec' in service_systemd_options_keys %} +{% if not 'RestartSec' in service_systemd_service_options_keys %} RestartSec=10s {% endif %} diff --git a/vars/main.yml b/vars/main.yml index e2ab7eb..7bdbb69 100644 --- a/vars/main.yml +++ b/vars/main.yml @@ -2,7 +2,3 @@ # vars file for docker_systemd_service docker_systemd_service_sysconf_dir: /etc/default docker_systemd_service_docker_path: "/usr/bin/docker" -docker_systemd_service_systemd_unit_options: - After: docker.service - PartOf: docker.service - Requires: docker.service -- 2.45.2