在CentOS 8机器上安装Redis之后,把它做成systemd服务的形式,实现开机自启。
Redis配置文件/etc/redis/redis.conf其中两个参数如下:

daemonize yes
supervised no

systemd的配置文件/etc/systemd/system/redis.service全文如下:

[Unit]
Description=redis-server
After=network.target

[Service]
Type=forking
ExecStart=/usr/local/bin/redis-server /etc/redis/redis.conf
PrivateTmp=true
User=redis
Group=redis
RuntimeDirectory=redis
RuntimeDirectoryMode=0755

[Install]
WantedBy=multi-user.target

配置完毕,直接在shell终端执行systemctl start redis进行测试服务,是能成功启动的。
接着
执行命令重新加载:systemctl daemon-reload
设置为开机自启:systemctl enable redis

开机之后查看Redis服务状态,却是失败:

[root@localhost ~]# systemctl status redis
● redis.service - redis-server
   Loaded: loaded (/etc/systemd/system/redis.service; enabled; vendor preset: disabled)
   Active: failed (Result: exit-code) since Thu 2021-10-14 08:36:17 EDT; 1min 9s ago
  Process: 1253 ExecStart=/usr/local/bin/redis-server /etc/redis/redis.conf (code=exited, status=0/SUCCESS)
 Main PID: 1267 (code=exited, status=1/FAILURE)

Oct 14 08:36:17 localhost.localdomain systemd[1]: Starting redis-server...
Oct 14 08:36:17 localhost.localdomain systemd[1]: Started redis-server.
Oct 14 08:36:17 localhost.localdomain systemd[1]: redis.service: Main process exited, code=exited, status=1/FAILURE
Oct 14 08:36:17 localhost.localdomain systemd[1]: redis.service: Failed with result 'exit-code'.

查看/var/log/messages日志,水平有限看不出明显的异常提示:

Oct 14 08:36:17 localhost systemd[1]: Started redis-server.
Oct 14 08:36:17 localhost systemd[1]: Started OpenSSH server daemon.
Oct 14 08:36:17 localhost NetworkManager[1243]: <info>  [1634214977.2267] settings: Loaded settings plugin: ifcfg-rh ("/usr/lib64/NetworkManager/1.20.0-3.el8/libnm-settings-plugin-ifcfg-rh.so")
Oct 14 08:36:17 localhost NetworkManager[1243]: <info>  [1634214977.2271] settings: Loaded settings plugin: keyfile (internal)
Oct 14 08:36:17 localhost systemd[1]: Starting Network Manager Script Dispatcher Service...
Oct 14 08:36:17 localhost systemd[1]: Started CUPS Scheduler.
Oct 14 08:36:17 localhost NetworkManager[1243]: <info>  [1634214977.2318] device (lo): carrier: link connected
Oct 14 08:36:17 localhost NetworkManager[1243]: <info>  [1634214977.2324] manager: (lo): new Generic device (/org/freedesktop/NetworkManager/Devices/1)
Oct 14 08:36:17 localhost NetworkManager[1243]: <info>  [1634214977.2348] manager: (ens33): new Ethernet device (/org/freedesktop/NetworkManager/Devices/2)
Oct 14 08:36:17 localhost systemd[1]: redis.service: Main process exited, code=exited, status=1/FAILURE
Oct 14 08:36:17 localhost systemd[1]: redis.service: Failed with result 'exit-code'.

尝试了百度多种解决方案,比如修改daemonize yes为no、supervised no为systemd,或者Type=simple、Type=notify等等,都无法解决,日志会出现其他的错误。

最后是增加了两行配置
After=network-online.target
Wants=network-online.target
才得以解决。修改后的systemd配置文件如下:

[root@localhost ~]# cat /etc/systemd/system/redis.service 
[Unit]
Description=redis-server
After=network.target
After=network-online.target    #增加
Wants=network-online.target    #增加

[Service]
Type=forking
ExecStart=/usr/local/bin/redis-server /etc/redis/redis.conf
PrivateTmp=true
User=redis
Group=redis
RuntimeDirectory=redis
RuntimeDirectoryMode=0755

[Install]
WantedBy=multi-user.target

要注意填写正确,如果某个字母漏了或者打错,是会失败的。

来自<systemd.special 中文手册>解释其含义:
network-online.target
对于那些严格要求 必须存在真实可用的网络连接的单元, 应该在其单元文件中包含 Wants=network-online.target 与 After=network-online.target 指令。 此目标单元意在包含 一个能够将执行流程一直阻塞到网络变为真实可用为止的服务单元。 具体的实现方法取决于网络管理服务所实际使用的网络管理工具。

注意,network-online.target 是一个主动单元(被功能使用者包含而不是被功能提供者包含), 它包含的服务单元可以将执行流程一直阻塞到网络变为真实可用为止。 相反,network.target 是一个被动单元(被功能提供者包含而不是被功能使用者包含), 它不会导致执行流程出现明显的阻塞。 一般来说, network.target 是系统启动流程中的一部分, 而 network-online.target 则不是(除非确有某些单元依赖于它)。 详情参见 Running Services After the Network is up 文档。

所有用于挂载远程网络文件系统的 mount 单元都自动包含 Wants=network-online.target 与 After=network-online.target 指令。 注意,仅向网络上其他主机提供服务的守护进程 通常并不依赖于此单元。

Wants=network-online.target 与 After=network-online.target 将被自动添加到所有引用了 “$network” 的SysV初始化脚本单元中。

注意,此单元仅用于系统启动期间。 系统启动完成之后, 此单元将不再跟踪系统的网络状态。 因此,不能将此单元用作网络连接监视器。

Logo

为开发者提供学习成长、分享交流、生态实践、资源工具等服务,帮助开发者快速成长。

更多推荐