1
0
Fork 0

Commits vergleichen

..

Keine gemeinsamen Commits. "31b5fa26a8fc7a5db31965e053f845189485e71c" und "3d528fe1a6e03c537669f7a70640b7a20ab82725" haben vollständig unterschiedliche Historien.

14 geänderte Dateien mit 138 neuen und 200 gelöschten Zeilen

Datei anzeigen

@ -1,26 +1,10 @@
=====================================
sebastian.systemd 0.4.3 Release Notes
sebastian.systemd 0.4.0 Release Notes
=====================================
.. contents:: Topics
v0.4.3
======
Changelog
---------
added new options to system_service
v0.4.2
======
Changelog
---------
upgraded to the new method used by sebastian.base
v0.4.0
======

Datei anzeigen

@ -9,7 +9,7 @@ docs: format
update-doc
release: changelog docs
ansible-galaxy collection build --output-path dist
ansible-galaxy collection build
upload: release
./upload.sh

Datei anzeigen

@ -66,11 +66,3 @@ releases:
release_date: "2024-02-24"
changes:
release_summary: added timer module
0.4.2:
release_date: "2024-03-09"
changes:
release_summary: upgraded to the new method used by sebastian.base
0.4.3:
release_date: "2024-03-09"
changes:
release_summary: added new options to system_service

Datei anzeigen

@ -1,7 +1,7 @@
---
namespace: sebastian
name: systemd
version: 0.4.3
version: 0.4.1
readme: README.md
@ -13,7 +13,7 @@ tags:
- systemd
- linux
dependencies:
sebastian.base: ">=0.4.0"
sebastian.base: ">=0.3.1"
repository: https://gitea.sebastian-tobie.de/ansible/ansible-systemd.git
# documentation: http://docs.example.com
homepage: https://gitea.sebastian-tobie.de/ansible/ansible-systemd

Datei anzeigen

@ -1,6 +1,6 @@
#!/usr/bin/python3
import pathlib
from typing import List, Optional
from typing import List
try:
from ansible_module.module_utils.generic import SYSTEMD_NETWORK_CONFIG, Types, modspec
@ -54,10 +54,10 @@ class Module(SystemdUnitModule): # type: ignore
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(self.match(), self.link())
self.__unit = "\n".join((self.match(), self.link()))
return self.__unit
def match(self) -> Optional[str]:
def match(self) -> str:
options = self.map_param(
mac="MACAddress",
permanentmac="PermanentAddress",
@ -67,11 +67,9 @@ class Module(SystemdUnitModule): # type: ignore
kind="Kind",
virtualization="Virtualization",
)
if len(options) == 0:
return None
return "[Match]\n" + "".join(options)
def link(self) -> Optional[str]:
def link(self) -> str:
options = []
if self.get("description", False):
options.append("Description={}\n".format(self.get("description", False)))
@ -79,8 +77,6 @@ class Module(SystemdUnitModule): # type: ignore
options.append("Name={}\n".format(self.get("name", False)))
if self.get("mtu", False):
options.append("MTUBytes={}\n".format(self.get("mtu", False)))
if len(options) == 0:
return None
return "[Link]\n" + "".join(options)
def post(self):

Datei anzeigen

@ -18,7 +18,7 @@ OPTION_MAPPING = dict(
@installable
class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore
"""Creates an systemd mount"""
name = "mount"
@ -45,25 +45,26 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(
self.header(),
self.mount(),
self.install(), # type: ignore[misc,call-arg]
self.__unit = "\n".join(
(
self.header(),
self.mount(),
self.install(),
)
)
return self.__unit
def header(self) -> str:
description = self.get("description", "Mount for {}".format(self.get("where")))
return f"[Unit]\nDescription={description}\n"
return "[Unit]\nDescription={}\n".format(self.get("description", "Mount for {}".format(self.get("where"))))
def mount(self) -> str:
options = []
options.append("Where={}\n".format(self.get("where")))
options.append("What={}\n".format(self.get("what")))
options.append("Type={}\n".format(self.get("fs")))
output = "[Mount]\n"
output += "Where={}\n".format(self.get("where"))
output += "What={}\n".format(self.get("what"))
output += "Type={}\n".format(self.get("fs"))
if self.get("options", False):
options.append("Options={}\n".format(",".join(self.get("options"))))
return "[Mount]\n" + "".join(options)
output += "Options={}\n".format(",".join(self.get("options")))
return output
DOCUMENTATION = """---

Datei anzeigen

@ -75,65 +75,55 @@ class Module(SystemdUnitModule):
parts = [self.match(), self.netdev()]
if kind != "dummy":
parts.append(getattr(self, kind)())
self.__unit = self._unit(*parts)
self.__unit = "\n".join(parts)
return self.__unit
def match(self) -> Optional[str]:
def match(self) -> str:
options = self.map_param(
host="Host",
kernelcmd="KernelCommandLine",
virtualization="Virtualization",
)
if len(options) == 0:
return None
return "[Match]\n" + "".join(options)
def netdev(self) -> Optional[str]:
def netdev(self) -> str:
options = self.map_param(
description="Description",
name="Name",
kind="Kind",
)
if len(options) == 0:
return None
return "[NetDev]\n" + "".join(options)
def bond(self) -> Optional[str]:
options = self.map_param(
mode="Mode",
minlinks="MinLinks",
def bond(self) -> str:
return "[Bond]\n" + "".join(
self.map_param(
mode="Mode",
minlinks="MinLinks",
)
)
if len(options) == 0:
return None
return "[Bond]\n" + "".join(options)
def bridge(self) -> Optional[str]:
options = self.map_param(
stp="STP",
priority="Priority",
def bridge(self) -> str:
return "[Bridge]\n" + "".join(
self.map_param(
stp="STP",
priority="Priority",
)
)
if len(options) == 0:
return None
return "[Bridge]\n" + "".join(options)
def wireguard(self) -> Optional[str]:
options = self.map_param(
privatekey="PrivateKey",
privatekeyfile="PrivateKeyFile",
port="ListenPort",
)
def wireguard(self) -> str:
port = self.get("port", False)
if port not in (False, "auto") and (port < 1 or port > 65535):
raise ValueError("Port must be between 0 and 65536")
if len(options) == 0:
return None
return "[Wireguard]\n" + "".join(options)
return "[Wireguard]\n" + "".join(
self.map_param(
privatekey="PrivateKey",
privatekeyfile="PrivateKeyFile",
port="ListenPort",
)
)
def vlan(self) -> Optional[str]:
options: list[str] = []
if len(options) == 0:
return None
return "[Vlan]\n" + "".join(options)
def vlan(self) -> str:
return ""
DOCUMENTATION = """---

Datei anzeigen

@ -1,6 +1,6 @@
#!/usr/bin/python3
import pathlib
from typing import List, Optional, Union
from typing import List, Union
try:
from ansible_module.module_utils.generic import SYSTEMD_NETWORK_CONFIG, Types, modspec, systemdbool
@ -36,7 +36,7 @@ class Module(SystemdUnitModule): # type: ignore
),
masquerade=Types.str(
help="how the packets are modified to look like the come from the computer itself.",
choices=("true", "false", "both", "ipv4", "ipv6", "no"),
choices=("true", "false", "both", "ipv4", "ipv6"),
),
),
required_if=(("defaultdns", True, ("dns",), False),),
@ -49,46 +49,56 @@ class Module(SystemdUnitModule): # type: ignore
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(
self.match(),
self.network(),
self.addresses(),
self.routes(),
self.__unit = "\n".join(
(
self.match(),
self.network(),
self.addresses(),
self.routes(),
)
)
return self.__unit
def match(self) -> Optional[str]:
matches = self.map_param(
mac="MACAddress",
device="Name",
virtualization="Virtualization",
def match(self) -> str:
matches = []
return "[Match]\n" + "".join(
self.map_param(
mac="MACAddress",
device="Name",
virtualization="Virtualization",
)
)
if len(matches) == 0:
return None
return "[Match]\n" + "".join(matches)
def network(self) -> Optional[str]:
def network(self) -> str:
output = "[Network]\n"
options = []
if self.get("description", None) is None:
try:
options.append("Description={}".format(self.get("description")))
server: str
for server in self.get("dns", []):
options.append(f"DNS={server}")
options.append("DNSDefaultRoute={}".format(self.get("defaultdns", False)))
if self.get("domain", False):
options.append("Domains={}".format(" ".join(self.get("domain"))))
except KeyError:
pass
try:
for server in self.get("dns", []):
options.append(f"DNS={server}")
options.append("DNSDefaultRoute={}".format(self.get("defaultdns", False)))
except KeyError:
pass
try:
domain = self.get("domain")
self.set("domainlog", str(domain))
options.append("Domains={}".format(" ".join(domain)))
options.append("DNSOverTLS={}".format(systemdbool(self.get("dot", "opportunistic"))))
options.append("DNSSEC={}".format(systemdbool(self.get("dnssec", "allow-downgrade"))))
if self.get("masquerade", None) is not None:
masquerade: str = self.get("masquerade")
except KeyError:
pass
if self.get("masquerade", -1) != -1:
masquerade = self.get("masquerade")
if masquerade == "true":
masquerade = "both"
elif masquerade == "false":
masquerade = "no"
options.append(f"IPMasquerade={masquerade}")
if len(options) == 0:
return None
return "[Network]\n" + "".join(options)
output += "\n".join(options)
return output
def addresses(self) -> str:
output = []
@ -96,13 +106,13 @@ class Module(SystemdUnitModule): # type: ignore
output.append(f"[Address]\nAddress={address}\n")
return "\n".join(output)
def routes(self) -> Optional[str]:
def routes(self) -> str:
output = []
routes: list[str] = self.get("route", [])
routes = self.get("route", [])
self.set("routes", routes)
for gw in routes:
output.append(f"[Route]\nGateway={gw}\nGatewayOnLink=yes\nQuickAck=yes\n")
if len(output) == 0:
return None
self.set("routes", output)
return "\n".join(output)
@ -195,7 +205,6 @@ options:
- both
- ipv4
- ipv6
- 'no'
description:
- how the packets are modified to look like the come from the computer itself.
required: false

Datei anzeigen

@ -1,6 +1,6 @@
#!/usr/bin/python3
import pathlib
from typing import List, Optional, Union
from typing import List, Union
try:
from ansible_module.module_utils.generic import SYSTEMD_SERVICE_CONFIG, Types, modspec
@ -47,26 +47,29 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore
self.unitfile = (SYSTEMD_SERVICE_CONFIG / self.get("name")).with_suffix(".socket")
self.__unit = None
def socket(self) -> Optional[str]:
section = self.map_param(
stream="ListenStream",
datagram="ListenDatagram",
sequential="ListenSequential",
fifo="ListenFIFO",
socketuser="SocketUser",
socketgroup="SocketGroup",
socketmode="SocketMode",
def socket(self):
section = "[Socket]\n"
section += "".join(
self.map_param(
stream="ListenStream",
datagram="ListenDatagram",
sequential="ListenSequential",
fifo="ListenFIFO",
socketuser="SocketUser",
socketgroup="SocketGroup",
socketmode="SocketMode",
)
)
if len(section) == 0:
return None
return "[Socket]\n" + "".join(section)
return section
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(
self.header(),
self.socket(),
self.install(), # type: ignore[call-arg,misc]
self.__unit = "\n".join(
(
self.header(),
self.socket(),
self.install(),
)
)
return self.__unit

Datei anzeigen

@ -11,7 +11,7 @@ except ImportError:
@installable
class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
class Module(SystemdUnitModule, SystemdReloadMixin):
"""Creates System Services units"""
name = "system_service"
@ -37,8 +37,6 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
required=True,
help="command or list of commands that are started as main programm. Multiple commands are only allowed in a oneshot command",
),
stop=Types.str(help="command that is started to stop the main program."),
remain=Types.bool(help="should the service remain as started after the command exited"),
post=Types.list(str, help="Command or list of commands that are started after the main command(s) stopped without problems."),
environmentfile=Types.list(
elements=str,
@ -88,11 +86,6 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
statedirectory=Types.str(
help="creates an unit specific state directory in /var/lib and sets the env var STATE_DIRECTORY with the path to it. Its cleaned up after the unit is stopped"
),
runtimedirectory=Types.str(
help="creates an unit specific runtime directory in /run and sets the env var RUNTIME_DIRECTORY with the path to it. Its cleaned up after the unit is stopped"
),
restart=Types.str(),
restartsec=Types.str(),
),
)
@ -102,7 +95,8 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
if self.get("type", "simple") != "oneshot" and len(self.get("start")) > 1:
self.module.fail_json("only oneshot services are allowed to have multiple start commands", **self.result)
def service(self) -> str:
def service(self):
section = "[Service]\n"
params = []
if self.get("environment", False):
for env in self.get("environment"):
@ -112,7 +106,6 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
type="Type",
pre="ExecStartPre",
start="ExecStart",
stop="ExecStop",
post="ExecStartPost",
serviceuser="User",
servicegroup="Group",
@ -126,21 +119,20 @@ class Module(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
execpath="ExecPaths",
noexecpath="NoExecPaths",
statedirectory="StateDirectory",
runtimedirectory="RuntimeDirectory",
nonewprivileges="NoNewPriviledges",
remain="RemainAfterExit",
restart="Restart",
restartsec="RestartSec",
)
)
return "[Service]\n" + "".join(params)
section += "".join(params)
return section
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(
self.header(),
self.service(),
self.install(), # type: ignore[call-arg,misc]
self.__unit = "\n".join(
(
self.header(),
self.service(),
self.install(),
)
)
return self.__unit
@ -254,7 +246,7 @@ options:
pre:
default: []
description:
- command or list of commands that are started before the main command
- command or list of commands that are started before the main command(Types.str)
elements: str
required: false
type: list
@ -280,11 +272,6 @@ options:
additionally /etc and if strict all except /proc, /sys and /dev
required: false
type: str
remain:
description:
- should the service remain as started after the command exited
required: false
type: bool
required_by:
default: []
description:
@ -300,12 +287,6 @@ options:
elements: str
required: false
type: list
restart:
required: false
type: str
restartsec:
required: false
type: str
ropath:
default: []
description:
@ -313,12 +294,6 @@ options:
elements: path
required: false
type: list
runtimedirectory:
description:
- creates an unit specific runtime directory in /run and sets the env var RUNTIME_DIRECTORY
with the path to it. Its cleaned up after the unit is stopped
required: false
type: str
rwpath:
default: []
description:
@ -351,11 +326,6 @@ options:
with the path to it. Its cleaned up after the unit is stopped
required: false
type: str
stop:
description:
- command that is started to stop the main program.
required: false
type: str
type:
choices:
- simple

Datei anzeigen

@ -13,7 +13,7 @@ __module_name__ = "TargetModule"
@installable
class TargetModule(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
class TargetModule(SystemdUnitModule, SystemdReloadMixin):
"""Creates Target units"""
name = "target"
@ -35,16 +35,16 @@ class TargetModule(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
def header(self) -> str:
section = super().header()
if section is None:
section = "[Unit]\n"
section += "AllowIsolate={}\n".format(systemdbool(self.get("allow_isolate", False)))
return section
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(
self.header(),
self.install(), # type: ignore[call-arg,misc]
self.__unit = "\n".join(
(
self.header(),
self.install(),
)
)
return self.__unit

Datei anzeigen

@ -14,7 +14,7 @@ __module_name__ = "TimerModule"
@installable
class TimerModule(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
class TimerModule(SystemdUnitModule, SystemdReloadMixin): # type: ignore
"""Creates Timer units"""
name = "timer"
@ -56,14 +56,14 @@ class TimerModule(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
unit=Types.str(help="The name of the unit. only needed if its not {{name}}.service"),
),
required_one_of=[
(
[
"onactive",
"onboot",
"onstartup",
"onunitactive",
"onunitinactive",
"oncalendar",
),
],
],
)
@ -82,23 +82,19 @@ class TimerModule(SystemdUnitModule, SystemdReloadMixin): # type: ignore[misc]
onunitactive="OnUnitActiveSec",
onunitinactive="OnUnitInactiveSec",
oncalendar="OnCalendar",
persistent="Persistent",
randomdelay="RandomizedDelaySec",
fixdelay="FixedRandomDelay",
unit="Unit",
),
)
if len(params) == 0:
return None
section += "".join(params)
return section
def unit(self) -> str:
if self.__unit is None:
self.__unit = self._unit(
self.header(),
self.body(),
self.install(), # type: ignore[call-arg,misc]
self.__unit = "\n".join(
(
self.header(),
self.body(),
self.install(),
)
)
return self.__unit

Datei anzeigen

@ -5,6 +5,3 @@ line-length = 140
atomic = true
profile = "black"
line_length = 140
[tool.mypy]
disable_error_code = ["import-untyped", "no-redef", "attr-defined"]

Datei anzeigen

@ -3,4 +3,4 @@ user=$(yq -r .namespace galaxy.yml)
package=$(yq -r .name galaxy.yml)
version=$(yq -r .version galaxy.yml)
printf "Namespace: %s\nPackage: %s\nVersion: %s\nfile name: %s\n" $user $package $version "$user-$package-$version.tar.gz"
ansible-galaxy collection publish dist/*
curl -u sebastian --upload-file "${user}-${package}-${version}.tar.gz" "https://gitea.sebastian-tobie.de/api/packages/ansible/generic/${package}/${version}/${user}-${package}-${version}.tar.gz"