为什么在 systemd 覆盖中的另一个 ExecStart=/new/value 之前使用 ExecStart=(没有值)?

Why use ExecStart= (with no value) before another ExecStart=/new/value in a systemd override?

我想通过 systemd 覆盖方式让 dockerd 监听端口 2376。 所以我跟着这个 instruction.

另一方面,我想深入了解 systemd 以了解幕后发生的事情。 所以我试图通过这个命令检查 docker 的单元文件: systemctl cat docker.service

根据命令的输出,涉及到两个文件

  1. /lib/systemd/system/docker.服务
  2. /etc/systemd/system/docker.service.d/override.conf

我相信第一个是 docker 的默认单元文件,第二个是我创建的。

我的问题是: 这两个文件都包含句子 - ExecStart= 并且在第二个文件中有两次,例如:

ExecStart=
ExecStart=/usr/bin/dockerd -H fd://

在设置有意义的值ExecStart=/usr/bin/dockerd -H fd://之前是否需要将空值赋给ExecStart=

我已将此 post 拆分为两个问题和另一个

当您将条目添加到覆盖文件时,它们默认 附加 到任何现有条目。也就是说,如果您的服务 example.service 具有:

[Service]
EnvironmentFile=/etc/foo.env

然后你创造 /etc/systemd/system/example.service.d/override.conf 有:

[Service]
EnvironmentFile=/etc/bar.env

则有效配置为:

[Service]
EnvironmentFile=/etc/foo.env
EnvironmentFile=/etc/bar.env

这对很多指令都很好,但一个服务只能有一个 ExecStart(除非它是 Type-oneshot 服务),因此如果您尝试创建这样的覆盖文件:

[Service]
ExecStart=/new/command/line

这将失败并出现如下错误:

systemd: example.service has more than one ExecStart= setting, which is only allowed for Type=oneshot services. Refusing.

通过指定一个 empty ExecStart,您正在“清除”所有 以前的条目。因此,如果您的 example.service 有:

[Service]
ExecStart=/bin/foo

然后您创建一个覆盖,例如:

[Service]
ExecStart=
ExecStart=/bin/bar

有效配置为:

[Service]
ExecStart=/bin/bar