我发现systemd-run
它允许一个人在后台运行进程一次(“瞬态服务”)。我总是用--unit $NAME
. 但是,如果我已经运行了systemd-run
命令并且我的进程正在运行,那么systemd-run
将失败,退出代码非零。无论如何,systemd-run
在这种情况下,是否有更多的幂等性并且不会失败?
目前我正在做:
systemctl is-active $NAME || systemd-run --unit $NAME $COMMAND
有没有更好的办法?
这是在 Ubuntu 18.04 上,使用当前的 systemd(版本 237?)
-G,--收集
完成后卸载瞬态单元,即使它失败了。通常,如果没有此选项,所有运行和失败的单元都会保存在内存中,直到用户使用 systemctl reset-failed 或等效命令明确重置其失败状态。另一方面,成功运行的单元会立即卸载。如果启用此选项,则单元的“垃圾收集”会更加激进,并且无论它们成功退出还是失败都会卸载单元。此选项是 --property=CollectMode=inactive-or-failed 的快捷方式,有关详细信息,请参阅 systemd.unit(5) 中对 CollectMode= 的说明。
我认为没有办法不失败。
这里的问题是 systemd 单元名称必须是唯一的。如果不是,那么操纵单位可能会变得模棱两可。出于这个原因,如果您尝试复制单位名称,systemd 会感知到错误,而且我认为没有办法让它不这么认为。
如果您可以说服
systemd-run
以相同的名称运行第二个服务,如果您发出systemctl stop
命令会发生什么?两个同名单位中的哪一个应该停止?你第一个跑的那个?最后?两个都?您需要
--collect
删除该单元(请参阅答案https://serverfault.com/a/1056478/161855)。这会引入轻微的TOCTOU,但总比没有好,并且
systemd-run
如果单元已经在运行,则不会导致打印错误。