https://www.digitalocean.com/community/tutorials/understanding-systemd-units-and-unit-files
介绍Linux 发行版越来越多地采用systemd 初始化系统。这套功能强大的软件可以管理服务器的许多方面,从服务到安装的设备和系统状态。 在systemd 中,unit 是指系统知道如何操作和管理的任何资源。目的是告诉systemd 工具知道如何处理。这些资源是使用称为Unit File 的配置文件定义的。 在本指南中,我们将向您介绍systemd 可以处理的不同 Unit。我们还将介绍可以在Unit文件中使用的许多指令中的一些指令,以便展示这些资源在您的系统上的处理方式。
Systemd Units作用Units 的目的是让systemd 知道如何管理。这些基本上是系统资源的标准化表示,可以由daemon管理,并由提供的实用程序操作。 Units可以说类似于其他init系统中的services或者jobs。但是,unit的定义要广泛得多,因为它们可用于抽象服务、网络资源、设备、文件系统挂载和独立资源池。 在其他 init 系统中可以用一个统一的服务定义处理的想法可以根据它们的重点分解成不同unit组件。按功能组织,允许您轻松启用、禁用或扩展功能,而无需修改Unit的核心行为。 Unit能够轻松实现的一些功能是:
- 基于套接字的激活(socket-based activation):与服务关联的套接字最好从守护程序本身中分离出来,以便单独处理。这提供了许多优点,例如延迟服务的启动,直到关联的套接字被首次访问。这也允许系统在引导过程的早期创建所有套接字,从而可以并行引导相关服务。
- 基于总线的激活(bus-based activation):Unit也可以在
D-Bus 提供的总线接口上激活。相关总线发布时启动Unit。 - 基于路径的激活(path-based activation):一个Unit可以根据某些文件系统路径的活动或可用性来启动。这利用了
inotify 。 - 基于设备的激活(device-based activation):Unit也可以通过利用
udev 事件在相关硬件首次可用时启动。 - 隐式依赖映射(implicit dependency mapping):大多数Unit的依赖树可以由
systemd 自己构建。您仍然可以添加依赖项和排序信息,但大部分繁重的工作都已为您完成。 - 实例和模板(instances and templates):模板Unit文件可用于创建同一通用Unit的多个实例。这允许所有相似unit可以提供相同的功能。
- 简单的安全加固(easy security hardening):Unit可以通过添加简单的指令来实现一些相当不错的安全功能。例如,您可以指定对部分文件系统没有访问权限或只读访问权限、限制内核功能以及分配私有
/tmp 和网络访问权限。 - 插件和片段(drop-ins and snippets):通过提供覆盖系统Unit文件部分的snippets,可以很容易地扩展unit。这使得在普通和自定义unit实现之间切换变得容易。
与其他 init 系统的工作项相比,systemd unit还有许多其他优势,但这应该让您了解使用原生配置指令可以发挥的强大功能。
System Unit文件路径定义systemd 如何处理Unit的文件可以在许多不同的位置找到,每个位置都有不同的优先级和含义。 系统的Unit文件副本通常保存在/lib/systemd/system 目录中。当软件在系统上安装Unit文件时,这是它们默认放置的位置。 存储在这里的Unit文件可以在会话期间按需启动和停止。这将是通用的普通Unit文件,通常由上游项目的维护者编写,应该在任何以标准实现方式部署 systemd 的系统上工作。您不应编辑此目录中的文件。相反,您应该覆盖该文件,如有必要,使用另一个Unit文件位置,该位置将取代该位置中的文件。 如果您希望修改Unit的运行方式,最好的位置是在/etc/systemd/system 目录中。在此目录位置中找到的Unit文件优先于文件系统上的任何其他位置。如果您需要修改系统的Unit文件副本,将替换文件放在该目录中是最安全、最灵活的方法。 如果您只想覆盖系统Unit文件中的特定指令,您实际上可以在子目录中提供Unit文件片段。这些将附加或修改系统副本的指令,允许您仅指定要更改的选项。 正确的做法是创建一个以Unit文件命名的目录,并在末尾附加.d 。因此,对于名为example.service 的Unit,可以创建一个名为example.service.d 的子目录。在此目录中,以.conf 结尾的文件可用于覆盖或扩展系统Unit文件的属性。
systemd 进程本身将此位置用于在运行时创建的动态创建的Unit文件。该目录可用于在会话期间更改系统的Unit行为。当服务器重新启动时,在此目录中所做的所有更改都将丢失。
Units 类型Systemd 根据它们描述的资源类型对Unit进行分类。确定Unit类型的最简单方法是使用其类型后缀,该后缀附加到资源名称的末尾。以下列表描述了 systemd 可用的单位类型:
.service : 服务Unit描述了如何管理服务器上的服务或应用程序。这将包括如何启动或停止服务,在什么情况下应该自动启动,以及相关软件的依赖和订购信息。.socket : 套接字Unit文件描述网络或 IPC 套接字,或systemd 用于基于套接字激活的 FIFO 缓冲区。这些总是有一个关联的.service 文件,当在该Unit定义的套接字上看到活动时,该文件将启动。.device : 一个描述设备的Unit,该设备已被udev 或sysfs 文件系统指定为需要systemd 管理。并非所有设备都有.device 文件。某些可能需要 .device Unit的场景是为了订购、安装和访问设备。.mount : 该Unit在系统上定义了一个由systemd 管理的挂载点。这些以挂载路径命名,斜线改为破折号。/etc/fstab 中的条目可以自动创建Unit。.aautomount : .automount Unit配置一个将自动挂载的挂载点。这些必须以它们引用的安装点命名,并且必须具有匹配的.mount Unit来定义安装的细节。.swap : 该Unit描述了系统上的交换空间。这些Unit的名称必须反映空间的设备或文件路径。.target : 目标Unit用于在启动或更改状态时为其他Unit提供同步点。它们也可用于使系统进入新状态。其他Unit指定它们与目标的关系,以与目标的操作相关联。.path : 该Unit定义了可用于基于路径的激活的路径。默认情况下,当路径到达指定状态时,将启动具有相同基本名称的.service Unit。这使用 inotify 来监视更改路径。.timer: 一个.timer Unit定义了一个由systemd 管理的计时器,类似于用于延迟或计划激活的cron 作业。当达到计时器时,将启动匹配Unit。.snapshot : .snapshot Unit由systemctl snapshot 命令自动创建。它允许您在进行更改后重建系统的当前状态。快照不会跨会话存在,用于回滚临时状态。.slice : .slice Unit与 Linux 控制组节点相关联,允许将资源限制或分配给与该片相关的任何进程。该名称反映了它在cgroup 树中的层次结构位置。默认情况下,Unit根据其类型放置在某些slice中。.scope : scope Unit由systemd 根据从其总线接口接收到的信息自动创建。这些用于管理在外部创建的系统进程集。
如您所见,systemd 知道如何管理许多不同的Unit。许多Unit类型一起工作以增加功能。例如,一些Unit用于触发其他Unit并提供激活功能。 我们将主要关注 .service Unit,因为它们的实用性和管理员需要管理这些Unit的一致性。
Unit 文件解析Unit文件的内部结构是按节(section)组织的。节由一对方括号[ 和] 表示,节(session)名称括在其中。每个部分都延伸到后续部分的开头或文件的结尾。
Unit文件通用特征部分名称定义明确且区分大小写。因此,如果拼写为[UNIT] ,[Unit] 部分将无法正确解释。如果您需要添加非标准部分以供systemd 以外的应用程序解析,您可以在部分名称中添加X- 前缀。 在这些部分中,Unit行为和元数据是通过使用键值格式的简单指令定义的,赋值由等号表示,如下所示:
[Section]
Directive1=value
Directive2=value
. . .
在覆盖文件(例如包含在unit.type.d 目录中的文件)的情况下,可以通过将指令分配给空字符串来重置指令。例如,系统的Unit文件副本可能包含一个设置为如下值的指令:
Directive1=default_value
default_value 可以通过引用不带值的Directive1 在覆盖文件中消除,如下所示:
Directive1=
一般来说,systemd 允许简单灵活的配置。例如,接受多个布尔表达式(1 、yes 、on 和 true 表示肯定,0 、no 、off 和 false 表示相反的答案)。可以智能地解析时间,假定秒为无单位值,并在内部完成多种格式的组合。
[Unit]部分大多数Unit文件中的第一部分是[Unit] 部分。这通常用于定义Unit的元数据和配置Unit与其他Unit的关系。 尽管在解析文件时,部分顺序对systemd 无关紧要,但此部分通常放在顶部,因为它提供了Unit的概览。您将在[Unit] 部分中找到的一些常见指令是:
Description= :该指令可用于描述Unit的名称和基本功能。它由各种systemd 工具返回,因此最好将其设置为简短、具体且信息丰富的内容。Documentation= :该指令为文档的 URI 列表提供了一个位置。这些可以是内部可用的手册页或 Web 可访问的 URL。systemctl status 命令将公开此信息,以便于发现。Requires= :这个指令列出了这个Unit本质上依赖的任何Unit。如果当前Unit被激活,此处列出的Unit也必须成功激活,否则该Unit将失败。默认情况下,这些Unit与当前Unit并行启动。 Wants= :该指令类似于Requires= ,但不那么严格。当该Unit被激活时,Systemd 将尝试启动此处列出的任何Unit。如果未找到这些Unit或无法启动,则当前Unit将继续运行。这是配置大多数依赖关系的推荐方法。同样,这意味着并行激活,除非被其他指令修改。BindsTo= :该指令类似于Requires= ,但也会导致当前Unit在关联Unit终止时停止。Before= :如果同时激活,则此指令中列出的Unit将不会启动,直到当前Unit被标记为已启动。这并不意味着依赖关系,如果需要,必须与上述指令之一结合使用。After= :该指令中列出的Unit将在启动当前Unit之前启动。这并不意味着依赖关系,如果需要,必须通过上述指令建立依赖关系。Conflicts= :这可用于列出不能与当前Unit同时运行的Unit。启动具有此关系的Unit将导致其他Unit停止。 Condition...= :有许多以Condition 开头的指令,允许管理员在启动Unit之前测试某些条件。这可用于提供仅在适当的系统上运行的通用Unit文件。如果不满足条件,则优雅地跳过该Unit。Assert...= :类似于以Condition 开头的指令,这些指令检查运行环境的不同方面,以决定是否应激活该Unit。但是,与 Condition 指令不同,否定结果会导致此指令失败。
使用这些指令和一些其他指令,可以建立有关Unit及其与其他Unit和操作系统的关系的一般信息。
[Install]部分在Unit文件的另一边,最后一部分通常是[Install] 部分。此部分是可选的,用于定义启用或禁用时的行为或Unit。启用一个Unit会将其标记为在启动时自动启动。本质上,这是通过将有问题的Unit锁定到另一个Unit上来实现的,该Unit位于要在引导时启动的Unit行中的某个位置。 因此,只有可以启用的Unit才会有此部分。其中的指令指示启用该Unit时应该发生什么:
WantedBy= :WantedBy= 指令是指定应如何启用Unit的最常用方法。该指令允许您以类似于[Unit] 部分中Wants= 指令的方式指定依赖关系。不同之处在于,该指令包含在辅助Unit中,允许列出的主要Unit保持相对清洁。当启用带有此指令的Unit时,将在/etc/systemd/system 中创建一个以指定Unit命名的目录,并在末尾附加.wants 。在其中,将创建一个指向当前Unit的符号链接,从而创建依赖关系。例如,如果当前Unit有WantedBy=multi-user.target ,一个名为multi-user.target.wants 的目录将在/etc/systemd/system 中创建(如果尚不可用)和一个指向当前Unit的符号链接会放在里面。禁用此Unit将删除链接并删除依赖关系。RequiredBy= :该指令与WantedBy= 指令非常相似,但它指定了一个必需的依赖项,如果不满足,将导致激活失败。启用后,具有此指令的Unit将创建一个以.requires 结尾的目录。Alias= :该指令也允许使用另一个名称启用该Unit。在其他用途中,这允许一个功能的多个提供者可用,以便相关Unit可以查找通用别名的任何提供者。 Also= :该指令允许将Unit作为一个集合启用或禁用。可以在此处列出当此Unit处于活动状态时应始终可用的支持Unit。它们将作为安装任务的组进行管理。 DefaultInstance= :对于可以生成具有不可预测名称的Unit实例的模板Unit(稍后介绍),如果未提供适当的名称,这可以用作名称的后备值。
Unit特定部分夹在前两个部分之间,您可能会发现特定于Unit类型的部分。大多数Unit类型提供仅适用于其特定类型的指令。这些在以其类型命名的部分中可用。我们将在这里简要介绍这些内容。
device 、target 、snapshot 和scope Unit类型没有特定于Unit的指令,因此没有与其类型相关联的部分。
[Service][Service] 部分用于提供仅适用于服务的配置。 应在[Service] 部分中指定的基本内容之一是服务的Type= 。这按服务的进程和守护进程行为对服务进行分类。这很重要,因为它告诉systemd 如何正确管理服务并找出其状态。
Type= 指令可以是以下之一:
simple :服务的主要进程在起始行指定。如果未设置Type= 和Busname= 指令,但设置了ExecStart= ,则这是默认值。任何通信都应通过适当类型的第二个Unit在Unit外部处理(如果该Unit必须使用套接字进行通信,则通过.socket Unit处理)。 forking :当服务分forck进程时使用此服务类型,几乎立即退出父进程。这告诉systemd 即使父进程退出,该进程仍在运行。oneshot :此类型表示该进程将是短暂的,systemd 应等待该进程退出,然后再继续其他Unit。这是默认的Type= 和ExecStart= 没有设置。它用于一次性任务。 dbus :这表示该Unit将在D-Bus 总线上取一个名称。发生这种情况时,systemd 将继续处理下一个Unit。notify :表示服务启动完成后会发出通知。systemd 进程将等待这种情况发生,然后再继续其他Unit。idle :这表示在所有作业都被调度之前,服务不会运行。
使用某些服务类型时可能需要一些额外的指令。例如:
RemainAfterExit= :该指令通常与 oneshot 类型一起使用。它表示即使在进程退出后,该服务也应被视为活动的。 PIDFile= :如果服务类型被标记为forking ,该指令用于设置文件的路径,该文件应包含应监视的主要子进程的进程 ID 号。BusName= :该指令应设置为服务在使用dbus 服务类型时将尝试获取的 D-Bus 总线名称。 notifyAccess = :这指定访问插座时应使用的套接字,该套接字在选择nofity 服务类型时可以侦听通知,可以是“none”,“ main”或“ all。all。默认值,“none”,忽略全部状态消息。“main”选项将监听来自主进程的消息,“all”选项将导致处理服务控制组的所有成员。
到目前为止,我们已经讨论了一些先决条件信息,但我们还没有真正定义如何管理我们的服务。执行此操作的指令是:
ExecStart= :这指定了启动进程要执行的命令的完整路径和参数。这只能指定一次(oneshot 服务除外)。如果命令路径前面有破折号- 字符,则将接受非零退出状态而不会将Unit激活标记为失败。ExecStartPre= :这可用于提供应在主进程启动之前执行的附加命令。这可以多次使用。同样,命令必须指定完整路径,并且可以在它们前面加上- 以指示将容忍命令失败。ExecStartPost= :这与ExecStartPre= 具有相同的特性,除了它指定将在主进程启动后运行的命令。ExecReload= :此可选指令指示重新加载服务配置所需的命令(如果可用)。ExecStop= :这表示停止服务所需的命令。如果没有给出,该进程将在服务停止时立即终止。 ExecStopPost= :这可用于指定在停止命令之后执行的命令。 RestartSec= :如果启用了自动重新启动服务,这指定了在尝试重新启动服务之前等待的时间量。Restart= :这表示systemd 将尝试自动重启服务的情况。这可以设置为“always”、“on-success”、“on-failure”、“on-abnormal”、“on-abort”或“on-watchdog”等值。这些将根据服务停止的方式触发重新启动。TimeoutSec= :这配置了systemd 在停止或停止服务之前将等待的时间,然后将其标记为失败或强行将其杀死。您也可以使用TimeoutStartSec= 和 TimeoutStopSec= 设置单独的超时。
[Socket]套接字Unit在systemd 配置中非常常见,因为许多服务实现基于套接字的激活以提供更好的并行性和灵活性。每个套接字Unit必须有一个匹配的服务Unit,当套接字接收到活动时,该服务Unit将被激活。 通过打破服务本身之外的套接字控制,可以提前初始化套接字,并且通常可以并行启动相关服务。默认情况下,套接字名称将在接收到连接时尝试启动同名服务。当服务初始化时,套接字将被传递给它,允许它开始处理任何缓冲的请求。 要指定实际的套接字,这些指令很常见:
ListenStream= :这为支持顺序、可靠通信的流套接字定义了一个地址。使用 TCP 的服务应该使用这种套接字类型。 ListenDatagram= :这为支持快速、不可靠通信数据包的数据报套接字定义了一个地址。使用 UDP 的服务应设置此套接字类型。 ListenSequentialPacket= :这定义了一个地址,用于与保留消息边界的最大长度数据报进行顺序、可靠的通信。这最常见于 Unix 套接字。 ListenFIFO :与其他侦听类型一起,您还可以指定 FIFO 缓冲区而不是套接字。
Listen 指令的类型更多,但以上几种是最常见的。 套接字的其他特性可以通过附加指令来控制:
Accept= :这决定是否为每个连接启动一个额外的服务实例。如果设置为 false(默认值),一个实例将处理所有连接。 SocketUser= :用一个Unix套接字,指定套接字的所有者。如果未设置,这将是根用户。 SocketGroup= :与Unix套接字,指定套接字的组所有者。如果这两个都没有设置,这将是根组。如果仅设置了SocketUser= ,systemd 将尝试查找匹配的组。 SocketMode= :对于 Unix 套接字或 FIFO 缓冲区,这将设置对创建的实体的权限。 Service= :如果服务名称与.socket 名称不匹配,则可以使用该指令指定服务。
[Mount]挂载Unit允许从systemd 中管理挂载点。挂载点以它们控制的目录命名,并应用了翻译算法。 例如,删除了前导斜杠,所有其他斜杠都被翻译成破折号- ,所有破折号和不可打印的字符都被替换为 C 风格的转义码。此翻译的结果用作安装Unit名称。安装Unit将隐式依赖于层次结构中位于其上方的其他安装。 挂载Unit通常在引导过程中直接从/etc/fstab 文件转换而来。对于自动创建的Unit定义和您希望在Unit文件中定义的Unit定义,以下指令很有用:
What= :需要挂载的资源的绝对路径。 where= :资源应该挂载的挂载点的绝对路径。这应该与Unit文件名相同,除了使用传统的文件系统符号。 Type= :挂载的文件系统类型。 Options= :任何需要应用的挂载选项。这是一个逗号分隔的列表。 SloppyOptions= :一个布尔值,用于确定如果存在无法识别的挂载选项,挂载是否会失败。 DirectoryMode= :如果挂载点需要创建父目录,这个决定了这些目录的权限模式。 TimeoutSec= :配置系统等待挂载操作被标记为失败的时间量。
[Automount]该Unit允许关联的 .mount Unit在引导时自动挂载。与 .mount Unit一样,这些Unit必须以翻译后的安装点路径命名。
[Automount] 部分非常简单,只允许使用以下两个选项:
Where= : 文件系统上自动挂载点的绝对路径。这将匹配文件名,除了它使用传统的路径符号而不是翻译。 DirectoryMode= :如果需要创建自动挂载点或任何父目录,这将决定那些路径组件的权限设置。
[Swap]交换Unit用于配置系统上的交换空间。这些Unit必须以交换文件或交换设备命名,使用与上面讨论的相同的文件系统翻译。 与挂载选项一样,交换Unit可以从/etc/fstab 条目自动创建,也可以通过专用Unit文件进行配置。 Unit文件的 [Swap] 部分可以包含以下配置指令:
What= :交换空间位置的绝对路径,无论是文件还是设备。Priority= :这需要一个整数,表示正在配置的交换的优先级。 Options= :通常在 /etc/fstab 文件中设置的任何选项都可以使用此指令来设置。使用逗号分隔的列表。TimeoutSec= :systemd 在将操作标记为失败之前等待交换被激活的时间量。
[Path]路径Unit定义了systmed 可以监视更改的文件系统路径。必须存在另一个Unit,当在路径位置检测到特定活动时,该Unit将被激活。路径活动是通过 inotify 事件确定的。 Unit文件的[Path] 部分可以包含以下指令:
PathExists= :该指令用于检查相关路径是否存在。如果是,则激活相关联的Unit。PathExistsGlob= :同上,但支持文件glob表达式判断路径是否存在。PathChanged= :这会监视路径位置的变化。如果在关闭监视的文件时检测到更改,则会激活关联的Unit。PathModified= :这会监视与上述指令类似的更改,但它会在文件写入和文件关闭时激活。DirectoryNotEmpty= :该指令允许systemd 在目录不再为空时激活关联的Unit。Unit= :这指定了当满足上面指定的路径条件时要激活的Unit。如果省略,systemd 将查找与该Unit共享相同基本Unit名称的.service 文件。MakeDirectory= :这决定了systemd 是否会在观看之前创建相关路径的目录结构。 DirectoryMode= :如果启用以上,这将设置必须创建的任何路径组件的权限模式。
[Time]定时器Unit用于安排任务在特定时间或在一定延迟后运行。该Unit类型替代或补充了cron 和at 守护进程的某些功能。必须提供相关联的Unit,该Unit将在到达计时器时激活。 Unit文件的[Timer] 部分可以包含以下一些指令:
OnActiveSec= :该指令允许关联Unit相对于 .timer Unit的激活被激活。 OnBootSec= :该指令用于指定系统启动后应激活关联Unit的时间量。 OnStartupSec= :这个指令类似于上面的计时器,但与 systemd 进程本身的启动时间有关。OnUnitActiveSec= :根据关联Unit上次激活的时间设置计时器。 OnUnitInactiveSec= :这将设置与关联Unit最后标记为非活动时间相关的计时器。OnCalendar= :这允许您通过指定相对于事件的绝对而不是相对来激活关联的单位。 AccuracySec= :该Unit用于设置计时器应遵守的精度级别。默认情况下,关联的Unit将在计时器到达后的一分钟内激活。该指令的值将确定systemd 安排激活发生的窗口的上限。Unit= :该指令用于指定计时器到时应激活的Unit。如果未设置,systemd 将查找名称与该Unit匹配的 .service Unit。Persistent= :如果设置了此项,systemd 将在定时器激活时触发关联的Unit,如果它在定时器处于非活动状态期间被触发的话。 WakeSystem= :设置此指令允许您在达到该状态时达到计时器时将系统从挂起状态唤醒。
[Slice]Unit文件的[Slice] 部分实际上没有任何.slice Unit特定配置。相反,它可以包含一些资源管理指令,这些指令实际上可用于上面列出的许多Unit。
[Slice] 部分中的一些常用指令,也可能在其他Unit中使用,可以在systemd.resource-control 手册页中找到。这些在以下特定于Unit的部分中有效:
[Slice] [Scope] [Service] [Socket] [Mount] [Swap]
从模板Unit文件创建实例Unit我们在本指南前面提到了使用模板Unit文件创建多个Unit实例的想法。在本节中,我们可以更详细地讨论这个概念。 在大多数方面,模板Unit文件与常规Unit文件没有什么不同。然而,这些通过允许文件的某些部分利用将在运行时可用的动态信息来提供配置Unit的灵活性。
模板和实例Unit名称可以识别模板Unit文件,因为它们在基本Unit名称之后和Unit类型后缀之前包含一个@ 符号。模板Unit文件名可能如下所示:
example@.service
从模板创建实例时,实例标识符位于@ 符号和表示Unit类型开始的句点之间。例如,上面的模板Unit文件可用于创建如下所示的实例Unit:
example@instance1.service
实例文件通常创建为模板文件的符号链接,链接名称包括实例标识符。这样,具有唯一标识符的多个链接可以指向单个模板文件。管理实例Unit时,systemd 将查找与您在命令行中指定的实例名称完全相同的文件以供使用。如果找不到,它将查找关联的模板文件。
模板特别参数模板Unit文件的强大之处主要体现在它能够根据操作环境在Unit定义中动态替换适当的信息。这是通过正常设置模板文件中的指令,但用变量说明符替换某些值或部分值来完成的。 以下是一些更常见的说明符,当用相关信息解释实例Unit时将被替换:
%n :在模板文件中出现的任何地方,将插入完整的结果Unit名称。 %N :这与上面的相同,但是任何转义,例如文件路径模式中的转义,都将被反转。%p :这引用了单位名称前缀。这是单位名称中@ 符号之前的部分。%P :这与上面相同,但任何转义都相反。%i :引用实例名,即实例Unit中@ 后面的标识符。这是最常用的说明符之一,因为它将保证是动态的。使用此标识符鼓励使用配置重要标识符。例如,服务将运行的端口可以用作实例标识符,模板可以使用此说明符来设置端口规范。%I :此说明符与上面的说明符相同,但任何转义都是相反的。%f :这将被替换为未转义的实例名称或前缀名称,前缀为/ 。%c :这将指示Unit的控制组,删除了 /sys/fs/cgroup/ssytemd/ 的标准父层次结构。 %u :配置为运行该Unit的用户的名称。%U :与上面相同,但作为数字 UID 而不是名称。%H :运行该Unit的系统的主机名。 %% :这用于插入文字百分号。
通过在模板文件中使用上述标识符,systemd 将在解释模板以创建实例Unit时填写正确的值。
总结使用 systemd 时,了解Unit和Unit文件可以使管理更容易。与许多其他 init 系统不同,您不必了解脚本语言来解释用于引导服务或系统的 init 文件。Unit文件使用相当简单的声明语法,让您一眼就能看出Unit在激活时的用途和效果。 将激活逻辑等功能分解为单独的Unit,不仅允许内部systemd 进程优化并行初始化,还使配置相当简单,并允许您修改和重新启动某些Unit,而无需拆除和重建它们的关联连接。利用这些能力可以在管理过程中为您提供更多的灵活性和权力。
|