您的位置:首页 > 运维架构 > Linux

Linux Systemd 详细介绍: Unit、Unit File、Systemctl、Target

2020-07-14 06:16 239 查看

Systemd
简介
CentOS 7 使用 Systemd 替换了SysV

Ubuntu 从 15.04 开始使用 Systemd

Systemd 是 Linux 系统工具,用来启动守护进程,已成为大多数发行版的标准配置

特点
优点:

按需启动进程,减少系统资源消耗

并行启动进程,提高系统启动速度

在 SysV-init 时代,将每个服务项目编号,依次执行启动脚本。Ubuntu 的 Upstart 解决了没有直接依赖的启动之间的并行启动。而 Systemd 通过 Socket 缓存、DBus 缓存和建立临时挂载点等方法进一步解决了启动进程之间的依赖,做到了所有系统服务并发启动。对于用户自定义的服务,Systemd 允许配置其启动依赖项目,从而确保服务按必要的顺序运行。

SystemV Upstart 参考上一篇博文:Linux 初始化系统 SystemV Upstart

使用 CGroup 监视和管理进程的生命周期

CGroup 提供了类似文件系统的接口,当进程创建子进程时,子进程会继承父进程的 CGroup。因此无论服务如何启动新的子进程,所有的这些相关进程都会属于同一个 CGroup

在 Systemd 之前的主流应用管理服务都是使用 进程树 来跟踪应用的继承关系的,而进程的父子关系很容易通过 两次 fork 的方法脱离。

而 Systemd 则提供通过 CGroup 跟踪进程关系,引补了这个缺漏。通过 CGroup 不仅能够实现服务之间访问隔离,限制特定应用程序对系统资源的访问配额,还能更精确地管理服务的生命周期

统一管理服务日志

支持快照和系统恢复

缺点:

过于复杂,与操作系统的其他部分强耦合,违反"keep simple, keep stupid"的Unix 哲学
架构图

Unit(单元|服务)
Systemd 可以管理所有系统资源:

将系统资源划分为12类
将每个系统资源称为一个 Unit。Unit 是 Systemd 管理系统资源的基本单位
使用一个 Unit File 作为 Unit 的单元文件,Systemd 通过单元文件控制 Unit 的启动
例如,MySQL服务被 Systemd 视为一个 Unit,使用一个 mysql.service 作为启动配置文件

Unit File(单元文件|配置文件)
单元文件中包含该单元的描述、属性、启动命令等

类型
Systemd 将系统资源划分为12类,对应12种类型的单元文件

系统资源类型 单元文件扩展名 单元文件描述
Service .service 封装守护进程的启动、停止、重启和重载操作,是最常见的一种 Unit 文件
Target .target 定义 target 信息及依赖关系,一般仅包含 Unit 段
Device .device 对于 /dev 目录下的硬件设备,主要用于定义设备之间的依赖关系
Mount .mount 定义文件系统的挂载点,可以替代过去的 /etc/fstab 配置文件
Automount .automount 用于控制自动挂载文件系统,相当于 SysV-init 的 autofs 服务
Path .path 用于监控指定目录或文件的变化,并触发其它 Unit 运行
Scope .scope 这种 Unit 文件不是用户创建的,而是 Systemd 运行时产生的,描述一些系统服务的分组信息
Slice .slice 用于表示一个 CGroup 的树
Snapshot .snapshot 用于表示一个由 systemctl snapshot 命令创建的 Systemd Units 运行状态快照,可以切回某个快照
Socket .socket 监控来自于系统或网络的数据消息
Swap .swap 定义一个用户做虚拟内存的交换分区
Timer .timer 用于配置在特定时间触发的任务,替代了 Crontab 的功能
对于操作单元文件的命令,如果缺省扩展名,则默认.service扩展名

而操作 target 的命令,例如 isolate,则默认.target扩展名

语法
单元文件的语法来源于 XDG桌面入口配置文件.desktop文件

Unit 文件可以分为三个配置区段:

Unit 段:所有 Unit 文件通用,用来定义 Unit 的元数据,以及配置与其他 Unit 的关系
Install 段:所有 Unit 文件通用,用来定义如何启动,以及是否开机启动
Service 段:服务(Service)类型的 Unit 文件(后缀为 .service)特有的,用于定义服务的具体管理和执行动作
单元文件中的区段名和字段名大小写敏感

每个区段内都是一些等号连接的键值对(键值对的等号两侧不能有空格)
http://www.sina.com.cn/mid/search.shtml?q=%E6%9E%9C%E5%8D%9A%E6%89%8B%E6%9C%BA%E7%89%88%E5%AE%98%E6%96%B9%E4%B8%8B%E8%BD%BD_18183615678
Unit 段
主要字段如下:

Description:当前服务的简单描述

Documentation:文档地址,可以是一个或多个文档的 URL 路径

【依赖关系】

Requires:与其它 Unit 的强依赖关系,如果其中任意一个 Unit 启动失败或异常退出,当前 Unit 也会被退出

Wants:与其它 Unit 的弱依赖关系,如果其中任意一个 Unit 启动失败或异常退出,不影响当前 Unit 继续执行

只涉及依赖关系,默认情况下 两个 Unit 同时启动

【启动顺序】

After:该字段指定的 Unit 全部启动完成以后,才会启动当前 Unit

Before:该字段指定的 Unit 必须在当前 Unit 启动完成之后再启动

只涉及启动顺序,不影响启动结果和运行情况

Binds To:与 Requires 相似,该字段指定的 Unit 如果退出,会导致当前 Unit 停止运行

Part Of:一个 Bind To 作用的子集,仅在列出的 Unit 失败或重启时,终止或重启当前 Unit,而不会随列出Unit 的启动而启动

http://www.sina.com.cn/mid/search.shtml?q=%E5%8D%8E%E7%BA%B3%E5%AE%A2%E6%9C%8D_18183615678__er

Install 段
主要字段如下:

WantedBy:它的值是一个或多个 target,执行enable命令时,符号链接会放入/etc/systemd/system目录下以 target 名 + .wants后缀构成的子目录中
RequiredBy:它的值是一个或多个 target,执行enable命令时,符号链接会放入/etc/systemd/system目录下以 target 名 + .required后缀构成的子目录中
Alias:当前 Unit 可用于启动的别名
Also:当前 Unit 被 enable/disable 时,会被同时操作的其他 Unit
http://www.sina.com.cn/mid/search.shtml?q=%E5%8D%8E%E7%BA%B3%E5%AE%A2%E6%9C%8D_18183615678__tg

Service 段
主要字段如下:

【启动类型】

Type:定义启动时的进程行为。它有以下几种值。
Type=simple:默认值,ExecStart字段启动的进程为主进程
服务进程不会 fork,如果该服务要启动其他服务,不要使用此类型启动,除非该服务是 socket 激活型
Type=forking:ExecStart字段将以fork()方式从父进程创建子进程启动,创建后父进程会立即退出,子进程成为主进程。
通常需要指定PIDFile字段,以便 Systemd 能够跟踪服务的主进程
对于常规的守护进程(daemon),除非你确定此启动方式无法满足需求,使用此类型启动即可
Type=oneshot:只执行一次,Systemd 会等当前服务退出,再继续往下执行
适用于只执行一项任务、随后立即退出的服务
通常需要指定RemainAfterExit=yes字段,使得 Systemd 在服务进程退出之后仍然认为服务处于激活状态
Type=dbus:当前服务通过 D-Bus 信号启动。当指定的 BusName 出现在 DBus 系统总线上时,Systemd认为服务就绪
Type=notify:当前服务启动完毕会发出通知信号,通知 Systemd,然后 Systemd 再启动其他服务
Type=idle:Systemd 会等到其他任务都执行完,才会启动该服务。
一种使用场合是:让该服务的输出,不与其他服务的输出相混合
【启动行为】

ExecStart:启动当前服务的命令

ExecStart=/bin/echo execstart1
ExecStart=
ExecStart=/bin/echo execstart2
顺序执行设定的命令,把字段置空,表示清除之前的值

ExecStartPre:启动当前服务之前执行的命令

ExecStartPost:启动当前服务之后执行的命令

ExecReload:重启当前服务时执行的命令

ExecStop:停止当前服务时执行的命令

ExecStopPost:停止当前服务之后执行的命令

RemainAfterExit:当前服务的所有进程都退出的时候,Systemd 仍认为该服务是激活状态

这个配置主要是提供给一些并非常驻内存,而是启动注册后立即退出,然后等待消息按需启动的特殊类型服务使用的
TimeoutSec:定义 Systemd 停止当前服务之前等待的秒数

注:所有的启动设置之前,都可以加上一个连词号(-),表示"抑制错误",即发生错误的时候,不影响其他命令的执行。比如,EnvironmentFile=-/etc/sysconfig/sshd(注意等号后面的那个连词号),就表示即使/etc/sysconfig/sshd文件不存在,也不会抛出错误。

【重启行为】

RestartSec:Systemd 重启当前服务间隔的秒数
KillMode:定义 Systemd 如何停止服务,可能的值包括:
control-group(默认值):当前控制组里面的所有子进程,都会被杀掉
process:只杀主进程(sshd 服务,推荐值)
mixed:主进程将收到 SIGTERM 信号,子进程收到 SIGKILL 信号
none:没有进程会被杀掉,只是执行服务的 stop 命令。
Restart:定义何种情况 Systemd 会自动重启当前服务,可能的值包括:
no(默认值):退出后不会重启
on-success:只有正常退出时(退出状态码为0),才会重启
on-failure:非正常退出时(退出状态码非0),包括被信号终止和超时,才会重启(守护进程,推荐值)
on-abnormal:只有被信号终止和超时,才会重启(对于允许发生错误退出的服务,推荐值)
on-abort:只有在收到没有捕捉到的信号终止时,才会重启
on-watchdog:超时退出,才会重启
always:不管是什么退出原因,总是重启
【上下文】

PIDFile:指向当前服务 PID file 的绝对路径。

User:指定运行服务的用户

Group:指定运行服务的用户组

EnvironmentFile:指定当前服务的环境参数文件。该文件内部的key=value键值对,可以用$key的形式,在当前配置文件中获取

启动sshd,执行的命令是/usr/sbin/sshd -D OPTIONS,其中的变量OPTIONS,其中的变量OPTIONS,其中的变量OPTIONS就来自EnvironmentFile字段指定的环境参数文件。
http://www.sina.com.cn/mid/search.shtml?q=%E5%8D%8E%E7%BA%B3%E5%85%AC%E5%8F%B8%E5%AE%A2%E6%9C%8D_18183615678_yn

占位符
在 Unit 文件中,有时会需要使用到一些与运行环境有关的信息,例如节点 ID、运行服务的用户等。这些信息可以使用占位符来表示,然后在实际运行中动态地替换为实际的值。

详细了解见 https://cloud.tencent.com/developer/article/1516125

模板
在现实中,往往有一些应用需要被复制多份运行,就会用到模板文件

模板文件的写法与普通单元文件基本相同,只是模板文件名是以 @ 符号结尾。例如:apache@.service

通过模板文件启动服务实例时,需要在其文件名的 @ 字符后面附加一个用于区分服务实例的参数字符串,通常这个参数是用于监控的端口号或控制台 TTY 编译号

systemctl start apache@8080.service
Systemd 在运行服务时,首先寻找跟单元名完全匹配的单元文件,如果没有找到,才会尝试选择匹配模板

例如上面的命令,System 首先会在约定的目录下寻找名为 apache@8080.service 的单元文件,如果没有找到,而文件名中包含 @ 字符,它就会尝试去掉后缀参数匹配模板文件。对于 apache@8080.service,Systemd 会找到 apache@.service 模板文件,并通过这个模板文件将服务实例化。

详细了解见 https://cloud.tencent.com/developer/article/1516125

状态
systemctl list-unit-files 将会列出文件的 state,包括 static, enabled, disabled, masked, indirect

masked

service软链接到/dev/null

该单元文件被禁止建立启动链接

static

该单元文件没有[Install]部分(无法执行),只能作为其他配置文件的依赖

enabled

已建立启动链接

disabled

没建立启动链接

https://askubuntu.com/a/731674

示例
关掉触摸板配置文件

Unit]
Description=Switch-off Touchpad

[Service]
Type=oneshot
ExecStart=/usr/bin/touchpad-off start
ExecStop=/usr/bin/touchpad-off stop
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target
oneshot 表明这个服务只要运行一次就够了,不需要长期运行
RemainAfterExit字段设为yes,表示进程退出以后,服务仍然保持执行。这样的话,一旦使用systemctl stop命令停止服务,ExecStop指定的命令就会执行,从而重新开启触摸板
Systemd 内建命令
systemd-analyze
Analyze and debug system manager, If no command is passed, Systemd-analyze time is implied
http://www.sina.com.cn/mid/search.shtml?q=%E5%8D%8E%E7%BA%B3%E5%85%AC%E5%8F%B8%E5%AE%A2%E6%9C%8D_18183615678__wf

systemd-analyze time
查看初始化耗时

systemd-analyze blame
打印所有运行单元,按它们初始化的时间排序。此信息可用于优化启动时间。注意,输出可能具有误导性,因为一个服务的初始化可能非常缓慢,因为它等待另一个服务的初始化完成

systemd-run

将一个指定的服务变成后台服务

未测试

参考 https://www.freedesktop.org/software/systemd/man/systemd-run.html

systemctl 系统服务管理命令
systemctl是 Systemd 的主命令,用于管理系统

与 service 命令的区别
systemctl 融合了 service 和 chkconfig 的功能
在 Ubuntu18.04 中没有自带 chkconfig 命令;service 命令实际上重定向到 systemctl 命令
动作 SysV Init 指令 Systemd 指令
启动某服务 service httpd start systemctl start httpd
停止某服务 service httpd stop systemctl stop httpd
重启某服务 service httpd restart systemctl restart httpd
检查服务状态 service httpd status systemctl status httpd
删除某服务 chkconfig --del httpd 停掉应用,删除其配置文件
使服务开机自启动 chkconfig --level 5 httpd on systemctl enable httpd
使服务开机不自启动 chkconfig --level 5 httpd off systemctl disable httpd
查询服务是否开机自启 chkconfig --list | grep httpd systemctl is-enabled httpd
加入自定义服务 chkconfig --add test systemctl load test
显示所有已启动的服务 chkconfig --list systemctl list-unit-files | grep enabled
参数
–all
显示加载到内存的所有单元

–type
-t --type=

显示指定类型(12种类型)的单元

–state
–state=

显示指定状态的单元或单元文件

单元状态

输入 systemctl list-units --state 按 Tab键,显示所有可用的值

单元文件状态

另外还可以用 enabled static disabled 等systemctl list-unit-files 显示的状态

–failed
–state=failed

显示加载失败的单元

systemctl --failed
–version
打印 Systemd 版本

lfp@legion:/lib/systemd/system$ systemctl --version
Systemd 237
+PAM +AUDIT +SELINUX +IMA +APPARMOR +SMACK +SYSVINIT +UTMP +LIBCRYPTSETUP +GCRYPT +GNUTLS +ACL +XZ +LZ4 +SECCOMP +BLKID +ELFUTILS +KMOD -IDN2 +IDN -PCRE2 default-hierarchy=hybrid
单元命令
我的理解

systemd 对单元的管理,不涉及单元文件自身属性和内容
list-units
相当于systemctl

列出当前已加载的单元(内存)

默认情况下仅显示处于激活状态(正在运行)的单元

UNIT 单元名

LOAD 加载状态

ACTIVE SUB 执行状态(大状态 子状态)

DESCRIPTION 描述

start
启动单元

systemctl start mysql.service
stop
停止单元

systemctl stop mysql.service
kill
杀掉单元进程

systemctl kill mysql.service
reload
不终止单元,重新加载 针对该单元的 运行配置文件,而不是 针对 systemd的 该单元的启动配置文件

例如启动 MySQL 服务,reload 可以在不停止服务的情况下重载 MySQL 的配置文件 my.cnf

restart
重启单元

该单元在重启之前拥有的资源不会被完全清空,比如文件描述符存储设施

systemctl reload mysql.service
status
status [unit | PID]

显示单元或进程所属单元的运行信息

systemctl status mysql.service
Loaded行:配置文件的位置,是否设为开机启动

Active行:表示正在运行

Main PID行:主进程ID

CGroup块:应用的所有子进程

日志块:应用的日志

is-active
判断指定的单元是否处于激活状态

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐