14.6 systemd及systemctl
Centos7 的服务管理工具

本节我们学习 Centos7 的开机启动程序 Systemd,及其服务管理工具 systemctl。我们会与 Centos6 中的 upstart 的启动程序对比来讲解。大家也可以参考阮一峰老师的博客。本节内容如下:
- Systemd 概述
 - Systemctl 命令的使用
 - Systemd 配置文件格式
 
1. Sysmted 概述:
MBR 架构的系统,开机启动过程是 POST --> Boot Sequeue(BIOS) --> Bootloader(MBR) --> Kernel(ramdisk) --> rootfs --> /sbin/init,而 Systemd 正是 Centos7 的/sbin/init 程序
1.2 Systemd的新特性
systemd 相比于 Centos5 的 SysV init,和 Centos 的 Upstart,具有如下特性:
- 新特性
- 系统引导时实现服务并行启动;
 - 按需激活进程;
 - 系统状态快照;
 - 基于依赖关系定义服务控制逻辑;
 
 - 关键特性:
- 基于socket的激活机制:socket与程序分离;
 - 基于bus的激活机制;
 - 基于device的激活机制;
 - 基于Path的激活机制;
 - 系统快照:保存各unit的当前状态信息于持久存储设备中;
 - 向后兼容sysv init脚本;/etc/init.d/
 - 不兼容:
- systemctl的命令是固定不变的;
 - 非由systemd启动的服务,systemctl无法与之通信;
 
 
 
1.2 服务配置
Sysv init 和 Upstart 中,服务的管理单元是一个个具有特定格式的 shell 脚本,由 service 命令统一进行管理。而 Systemd 中服务的核心单元叫 Unit,unit 由其相关配置文件进行标识、识别和配置,配置文件中主要包含了系统服务、监听的socket、保存的快照以及其它与init相关的信息。systemd 按照功能将 unit 分为了如下几种类型。
unit的常见类型
| 类型 | 文件扩展名 | 作用 | 
|---|---|---|
| Service unit | .service | 用于定义系统服务 | 
| Target unit | .target | 用于模拟实现运行级别 | 
| Device unit | .device | 用于定义内核识别的设备 | 
| Mount unit | .mount | 定义文件系统挂载点 | 
| Socket unit | .socket | 用于标识进程间通信用到的socket文件 | 
| Snapshot unit | .snapshot | 管理系统快照 | 
| Swap unit | .swap | 用于标识swap设备 | 
| Automount unit | .automount | 文件系统自动点设备 | 
| Path unit | .path | 用于定义文件系统中的一文件或目录 | 
systemd 的配置文件
systemd 的配置文件位于以下三个目录中
/usr/lib/systemd/system: 实际配置文件的存存放位置/run/systemd/system:不常用/etc/systemd/system: 基本上都是软连接
对于那些支持 Systemd 的软件,安装的时候,会自动在/usr/lib/systemd/system目录添加一个配置文件。
如果你想让该软件开机启动,就执行下面的命令(以httpd.service为例)。
 | 
 | 
上面的命令相当于在 /etc/systemd/system 目录添加一个符号链接,指向 /usr/lib/systemd/system 里面的httpd.service文件。
这是因为开机时,Systemd只执行 /etc/systemd/system 目录里面的配置文件。这也意味着,如果把修改后的配置文件放在该目录,就可以达到覆盖原始配置的效果。
除了使用普通的文本查看命令外查看配置文件外,systemctl cat NAME.service 可通过服务名称直接查看配置文件
 | 
 | 
2. systemctl 命令使用
2.1 管理系统服务 (service unit)
systemctl  [OPTIONS...]  COMMAND  [NAME...]
- OPTIONS:
-t, --type=: 指定查看的 unit 类型-a, --all:查看所由服务
 
服务启动与关闭
| 作用 | init | systemctl | 
|---|---|---|
| 启动 | service NAME start | systemctl start NAME.service | 
| 停止 | service NAME stop | systemctl stop NAME.service | 
| 重启 | service NAME restart | systemctl restart NAME.service | 
| 状态 | service NAME status | systemctl status NAME.service | 
| 条件式重启 | service NAME condrestart | systemctl try-restart NAME.service | 
| 重载或重启服务 | systemctl reload-or-restart NAME.servcie | |
| 重载或条件式重启服务 | systemctl reload-or-try-restart NAME.service | 
 | 
 | 
输出:
- Loaded行:配置文件的位置,是否设为开机启动
 - Active行:表示正在运行
 - Main PID行:主进程ID
 - Status行:由应用本身(这里是 httpd )提供的软件当前状态
 - CGroup块:应用的所有子进程
 - 日志块:应用的日志
 
服务状态查看
| 作用 | init | systemctl | 
|---|---|---|
| 查看某服务当前激活与否的状态 | systemctl is-active NAME.service | |
| 查看所有已激活的服务 | systemctl list-units –type service | |
| 查看所有服务(已激活及未激活) | systemctl list-units -t service –all | 
开机自启
| 作用 | init | systemctl | 
|---|---|---|
| 设置服务开机自启 | chkconfig NAME on | systemctl enable NAME.service | 
| 禁止服务开机自启 | chkconfig NAME off | systemctl disable NAME.service | 
| 查看某服务是否能开机自启 | chkconfig –list NAME | systemctl is-enabled NAME.service | 
| 查看所有服务的开机自启状态 | chkconfig –list | systemctl list-unit-files –type service | 
| 禁止某服务设定为开机自启 | systemctl mask NAME.service | |
| 取消此禁止 | systemctl unmask NAME.servcie | 
依赖关系
| 作用 | init | systemctl | 
|---|---|---|
| 查看服务的依赖关系 | systemctl list-dependencies NAME.service | 
2.2 管理 target units
| 作用 | init | systemctl | 
|---|---|---|
| 运行级别 | 0 | runlevel0.target, poweroff.target | 
| 运行级别 | 1 | runlevel1.target, rescue.target | 
| 运行级别 | 2 | runlevel2.tartet, multi-user.target | 
| 运行级别 | 3 | runlevel3.tartet, multi-user.target | 
| 运行级别 | 4 | runlevel4.tartet, multi-user.target | 
| 运行级别 | 5 | runlevel5.target, graphical.target | 
| 运行级别 | 6 | runlevel6.target, reboot.target | 
| 级别切换 | init N | systemctl isolate NAME.target | 
| 查看级别 | runlevel | systemctl list-units –type target | 
| 查看所有级别 | systemctl list-units -t target -a | |
| 获取默认运行级别 | /etc/inittab | systemctl get-default | 
| 修改默认运行级别 | /etc/inittab | systemctl set-default NAME.target | 
| 切换至紧急救援模式 | systemctl rescue | |
| 切换至emergency模式 | systemctl emergency | 
2.3 其它常用快捷命令
- 关机: 
systemctl halt,systemctl poweroff - 重启: 
systemctl reboot - 挂起: 
systemctl suspend - 快照: 
systemctl hibernate - 快照并挂起: 
systemctl hybrid-sleep 
3. service unit file 配置
3.1 unit file 组成
unit file 通常由如下 三个部分组成:
- [Unit]:
- 定义与Unit类型无关的通用选项;
 - 用于提供 unit 的描述信息、unit 行为及依赖关系等;
 
 - [Service]:
- 与特定类型相关的专用选项;此处为 Service 类型;
 
 - [Install]:
- 定义由
systemctl enable以及systemctl disable命令在实现服务启用或禁用时用到的一些选项; 
 - 定义由
 
 | 
 | 
Unit段
Description:当前服务的简单描述After:定义unit的启动次序;表示当前unit应该晚于哪些unit启动;其功能与Before相反;Before:定义sshd.service应该在哪些服务之前启动Requies:依赖到的其它units;强依赖,被依赖的units无法激活或异常退出时,当前unit即无法激活;Wants:依赖到的其它units;弱依赖,被依赖的units无法激活时,不影响当 unit 的启动;Conflicts:定义units间的冲突关系;- 附注:
- After和Before字段只涉及启动顺序,不涉及依赖关系
 - Wants字段与Requires字段只涉及依赖关系,与启动顺序无关,默认情况下是同时启动的
 
 
Service段
Type:用于定义影响ExecStart及相关参数的功能的unit进程启动类型;simple(默认值):ExecStart字段启动的进程为主进程forking:ExecStart字段将以fork()方式启动,此时父进程将会退出,子进程将成为主进程oneshot:类似于simple,但只执行一次,Systemd 会等它执行完,才启动其他服务dbus:类似于simple,但会等待 D-Bus 信号后启动notify:类似于simple,启动结束后会发出通知信号,然后 Systemd 再启动其他服务idle:类似于simple,但是要等到其他任务都执行完,才会启动该服务。一种使用场合是为让该服务的输出,不与其他服务的输出相混合
EnvironmentFile:指定当前服务的环境参数文件ExecStart:指明启动unit要运行命令或脚本;其中的变量$OPTIONS就来自EnvironmentFile字段指定的环境参数文件ExecReload:重启服务时执行的命令ExecStop:停止服务时执行的命令ExecStartPre:启动服务之前执行的命令ExecStartPost:启动服务之后执行的命令ExecStopPost:停止服务之后执行的命令Restart:定义了服务退出后,Systemd 的重启方式no(默认值):退出后不会重启on-success:只有正常退出时(退出状态码为0),才会重启on-failure:非正常退出时(退出状态码非0),包括被信号终止和超时,才会重启on-abnormal:只有被信号终止和超时,才会重启on-abort:只有在收到没有捕捉到的信号终止时,才会重启on-watchdog:超时退出,才会重启always:不管是什么退出原因,总是重启- 附注: 对于守护进程,推荐设为on-failure。对于那些允许发生错误退出的服务,可以设为on-abnormal
 
KillMode:定义 Systemd 如何停止服务control-group(默认值):当前控制组里面的所有子进程,都会被杀掉process:只杀主进程mixed:主进程将收到 SIGTERM 信号,子进程收到 SIGKILL 信号none:没有进程会被杀掉,只是执行服务的 stop 命令。
RestartSec:表示 Systemd 重启服务之前,需要等待的秒数
对于 sshd 服务而言将KillMode设为process,表示只停止主进程,不停止任何sshd 子进程,即子进程打开的 SSH session 仍然保持连接。这个设置不太常见,但对 sshd 很重要,否则你停止服务的时候,会连自己打开的 SSH session 一起杀掉。Restart设为on-failure,表示任何意外的失败,就将重启sshd。如果 sshd 正常停止(比如执行systemctl stop命令),它就不会重启。
所有的启动设置之前,都可以加上一个连词号(-),表示"抑制错误",即发生错误的时候,不影响其他命令的执行。比如,EnvironmentFile=-/etc/sysconfig/sshd(注意等号后面的那个连词号),就表示即使/etc/sysconfig/sshd文件不存在,也不会抛出错误
Install段
Alias:RequiredBy:被哪些units所依赖;WantedBy:表示该服务所在的 Target
3.2 修改配置文件后重启
对于新创建的unit文件或修改了的unit文件,要通知systemd重载此配置文件 systemctl  daemon-reload
4.Target 的配置文件
 | 
 | 
Target 配置文件里面没有启动命令
Requires:要求basic.target一起运行。Conflicts:冲突字段。如果rescue.service或rescue.target正在运行,multi-user.target就不能运行,反之亦然。After:表示multi-user.target在basic.target 、 rescue.service、 rescue.target之后启动,如果它们有启动的话。AllowIsolate:允许使用systemctl isolate命令切换到multi-user.target