Add ability to create templated services

This functionality is pretty neat and used widely if you need to pass
specific argument to the unit service, but rest of the parameters can
be left intact.

Change-Id: I6eb80ac0f9f0257402697a255518bb2c66d0dfd5
This commit is contained in:
Dmitriy Rabotyagov 2021-11-03 18:19:22 +02:00
parent 17852bc111
commit 1f7091a11c
7 changed files with 101 additions and 27 deletions

View File

@ -114,6 +114,10 @@ systemd_environment: {}
# `environment` -- (optional) set additional environment settings, this option is a hash of strings.
# `environment_file` -- (optional) set additional environment settings through a given file. this option is a string.
# `dynamic_user` -- (optional) Dynamically set a UNIX user and group when the unit is started; only works if systemd >= 235.
# `template_arguments` -- (optional) List of arguments that would be enabled/started in case service is a template.
# For that to work properly, service_name should end with `@`, ie `dhcpcd@`
# Systemd service template documentation can be found by the link:
# https://www.freedesktop.org/software/systemd/man/systemd.service.html#Service%20Templates
# `state_directory` -- (optional) Relative path the state directory; only works if systemd >= 235.
# `systemd_overrides` -- (optional) Dictionary that may contain custom structure in config_overrides format that
# will be used to generate systemd overrides in /etc/systemd/system/service_name.service.d/overrides.conf
@ -238,4 +242,12 @@ systemd_environment: {}
# - ServiceZ
# - ServiceY
# restart_changed: no
#
# Example below will result in creating 2 templated services: Templated@arg1 and Templated@arg2
# - service_name: Templated@
# execstarts:
# - /tmp/script %i
# template_arguments:
# - arg1
# - arg2
systemd_services: []

View File

@ -14,15 +14,15 @@
# limitations under the License.
- name: Restart changed services
systemd:
name: "{{ item.item.service_name | replace(' ', '_') }}.{{ (item.item.timer is defined) | ternary('timer', 'service') }}"
state: restarted
include_tasks: handlers/systemd_restart.yml
listen: systemd service changed
with_items: "{{ systemd_services_result.results }}"
when:
- 'item.item.restart_changed | default(systemd_service_restart_changed) | bool'
- 'item.item.state is not defined'
- 'item.item.enabled | default(systemd_service_enabled) | bool'
- 'item is changed'
- 'services_results.item.restart_changed | default(systemd_service_restart_changed) | bool'
- 'services_results.item.state is not defined'
- 'services_results.item.enabled | default(systemd_service_enabled) | bool'
- 'services_results is changed'
loop: "{{ systemd_services_result.results }}"
loop_control:
loop_var: services_results
tags:
- systemd-service

View File

@ -0,0 +1,22 @@
---
# Copyright 2021, City Network International AB.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
- name: "Restart service {{ services_results.item.service_name | replace(' ', '_') }}"
systemd:
name: "{{ services_results.item.service_name | replace(' ', '_') }}{{ template_argument }}.{{ (services_results.item.timer is defined) | ternary('timer', 'service') }}"
state: restarted
loop: "{{ services_results.item.template_arguments | default(['']) }}"
loop_control:
loop_var: template_argument

View File

@ -0,0 +1,7 @@
---
features:
- |
Allow to create `templated services <https://www.freedesktop.org/software/systemd/man/systemd.service.html#Service%20Templates>`_
Now for systemd_services you are allowed to provide template_arguments,
which can contain a list of arguments with which templated services
would be created.

View File

@ -140,25 +140,10 @@
when:
- (systemd_services_result is changed) or (systemd_timer_result is changed) or ('true' in systemd_socket.results | map(attribute='changed') | list )
- name: Load service
systemd:
name: "{{ item.service_name | replace(' ', '_') }}.service"
enabled: "{{ item.enabled | default(systemd_service_enabled) }}"
state: "{{ (item.timer is defined) | ternary(omit, (item.state | default(omit))) }}"
with_items: "{{ systemd_services }}"
when:
- item.load | default(True)
tags:
- systemd-service
- name: Load timer
systemd:
name: "{{ item.service_name | replace(' ', '_') }}.timer"
enabled: "{{ item.enabled | default(systemd_service_enabled) }}"
state: "{{ item.timer.state | default(omit) }}"
when:
- item.timer is defined
with_items: "{{ systemd_services }}"
- include_tasks: systemd_load.yml
loop: "{{ systemd_services }}"
loop_control:
loop_var: service
tags:
- systemd-service

39
tasks/systemd_load.yml Normal file
View File

@ -0,0 +1,39 @@
---
# Copyright 2021, City Network International AB.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# NOTE(noonedeadpunk): If we don't have template_arguments set, we just iterate over list with
# empty string as element. This won't have any effect on the results, but
# we reduce code duplication
- name: "Load service {{ service.service_name | replace(' ', '_') }}"
systemd:
name: "{{ service.service_name | replace(' ', '_') }}{{ template_argument }}.service"
enabled: "{{ service.enabled | default(systemd_service_enabled) }}"
state: "{{ (service.timer is defined) | ternary(omit, (service.state | default(omit))) }}"
when:
- service.load | default(True)
loop: "{{ service.template_arguments | default(['']) }}"
loop_control:
loop_var: template_argument
- name: "Load timer {{ service.service_name | replace(' ', '_') }}"
systemd:
name: "{{ service.service_name | replace(' ', '_') }}{{ template_argument }}.timer"
enabled: "{{ service.enabled | default(systemd_service_enabled) }}"
state: "{{ service.timer.state | default(omit) }}"
when:
- service.timer is defined
with_items: "{{ service.template_arguments | default(['']) }}"
loop_control:
loop_var: template_argument

View File

@ -64,6 +64,15 @@
state: "started"
cron_minute: 30
cron_hour: 1
- service_name: "test_templated_service@"
service_type: oneshot
execstarts:
- "/bin/bash -c 'echo %i'"
template_arguments:
- 1
- 2
enabled: yes
state: started
post_tasks:
- name: Check Services