Tob*_*oby 8 systemd services sysvinit autostart
我一直在解决 sysVinit 服务在 systemd 环境中启动时无法正常联机的问题。我发现,当 /etc/systemd/system/ 中不存在上述服务的服务文件或覆盖时,它会正确自动启动。在这种情况下,据我所知,systemd 应该通过读取系统上存在的“遗留”sysvinit 脚本来动态加载启动脚本,尽管我不是 100% 清楚这一点。
我感到困惑的是,一旦我将 edit --full 选项传递给 systemctl 用于所述服务,就会在 /etc/systemd/system/ 中生成一个平面文件,并且该服务现在无法在启动时自动启动。使用编辑选项并尝试添加任何覆盖似乎也会导致服务无法启动。
如果需要,请在下面提供示例...
系统运行时的示例:
在此示例中,名为“ProgramExample”的服务在 /etc/init.d/programexample 和 /etc/rc.d/init.d/programexample 中有一个 init 脚本:
[root@centos7-box ~]# ls -l /etc/rc.d/init.d/programexample
-rwxr-xr-x. 1 root root 2264 Mar 29 14:11 /etc/rc.d/init.d/programexample
Run Code Online (Sandbox Code Playgroud)
/etc/systemd/system/ 中没有服务文件:
[root@centos7-box ~]# ls -lh /etc/systemd/system/programexample.service
ls: cannot access /etc/systemd/system/programexample.service: No such file or directory
Run Code Online (Sandbox Code Playgroud)
此配置中的 Systemctl 状态输出:
[root@centos7-box ~]# systemctl status programexample.service
? programexample.service - LSB: Start Program Example at boot time
Loaded: loaded (/etc/rc.d/init.d/programexample; bad; vendor preset: disabled)
Active: active (exited) since Wed 2017-03-29 15:53:06 CDT; 14min ago
Docs: man:systemd-sysv-generator(8)
Process: 1297 ExecStart=/etc/rc.d/init.d/programexample start (code=exited, status=0/SUCCESS)
Mar 29 15:53:05 centos7-box systemd[1]: Starting LSB: Start ProgramExample at boot time...
Mar 29 15:53:05 centos7-box su[1307]: (to programexample) root on none
Mar 29 15:53:06 centos7-box programexample[1297]: ProgramExample (user programexample): instance name set to centos7-box
Mar 29 15:53:06 centos7-box programexample[1297]: instance public base uri set to https://192.168.0.148.programexample.net/programexample/
Mar 29 15:53:06 centos7-box programexample[1297]: instance timezone set to US/Central
Mar 29 15:53:06 centos7-box programexample[1297]: starting java services
Mar 29 15:53:06 centos7-box programexample[1297]: ProgEx server started.
Mar 29 15:53:06 centos7-box systemd[1]: Started LSB: Start ProgramExample at boot time.
Run Code Online (Sandbox Code Playgroud)
使用上述配置,无需在 /etc/systemd/system/ 中创建/放置任何文件,ProgramExample 服务即可正常自动启动。
一旦使用 systemctl edit --full (或只是编辑):
将任何编辑传递给 systemctl 后,我观察到以下情况:
此配置中的 Systemctl 状态输出(编辑后):
[root@centos7-box ~]# systemctl status programexample.service
? programexample.service - LSB: Start ProgramExample at boot time
Loaded: loaded (/etc/rc.d/init.d/programexample; static; vendor preset: disabled)
Active: inactive (dead)
Docs: man:systemd-sysv-generator(8)
Run Code Online (Sandbox Code Playgroud)
这是使用 -edit --full 选项时生成并放置在 /etc/systemd/system/ 中的服务文件:
# Automatically generated by systemd-sysv-generator
[Unit]
Documentation=man:systemd-sysv-generator(8)
SourcePath=/etc/rc.d/init.d/programexample
Description=LSB: Start ProgramExample at boot time
Before=runlevel2.target
Before=runlevel3.target
Before=runlevel4.target
Before=runlevel5.target
Before=shutdown.target
Before=adsm.service
After=all.target
After=network-online.target
After=postgresql-9.4.service
Conflicts=shutdown.target
[Service]
Type=forking
Restart=no
TimeoutSec=5min
IgnoreSIGPIPE=no
KillMode=process
GuessMainPID=no
RemainAfterExit=yes
ExecStart=/etc/rc.d/init.d/programexample start
ExecStop=/etc/rc.d/init.d/programexample stop
ExecReload=/etc/rc.d/init.d/programexample reload
Run Code Online (Sandbox Code Playgroud)
这里发生了什么?如果没有 /etc/systemd/system/ 中的平面服务文件和/或服务覆盖目录,systemd 正在从所述服务的 init 脚本动态读取此信息,我是否正确?我已经尝试了多次在 /etc/systemd/system/ 编辑服务文件并保留默认文件的迭代,但无法使自动启动工作或服务进入“启用”状态。
我认为最好有一个 systemd .service 文件用于 systemd 配置,而不是依赖 systemd 从 init 脚本 LSB 标头中读取出于兼容性和并发性的原因,但是 systemd 创建的默认文件无法启动或启用以及许多其他我尝试过的 .service 文件的更简单迭代。
我现在发现问题是 systemd-sysv-generator 自动生成的服务文件缺少带有 WantedBy 选项的安装部分。我将以下内容添加到我在 /etc/systemd/system/programexample.service 生成的文件中,这使我能够正确启用该服务:
[Install]
WantedBy = multi-user.target
Run Code Online (Sandbox Code Playgroud)
之后我跑了
systemctl daemon-reload
Run Code Online (Sandbox Code Playgroud)
确保我的服务文件被 systemd 读取。
现在我收到了一个正确的通知,我的服务实际上在某处被符号链接为“启用”:
[root@centos7-box ~]# systemctl enable programexample.service
Created symlink from /etc/systemd/system/multi-user.target.wants/programexample.service to /etc/systemd/system/programexample.service.
Run Code Online (Sandbox Code Playgroud)
此链接帮助我更好地了解服务文件。
我不喜欢 systemd-sysv-generator 默认情况下不包含带有 WantedBy 选项的安装部分。如果 systemd 可以动态读取 LSB 标头并在启动时正确启动服务,为什么它不相应地生成服务文件?我想一些系统性成长的痛苦是可以预料的。
2020 年 7 月 7 日更新:
与 Debian Buster 合作并尝试启用 SysVInit 遗留服务时,我看到了这条精彩的消息,我相信这会为我在 2017 年处理这个问题时节省一些时间:
Synchronizing state of programexample.service with SysV service script with /lib/systemd/systemd-sysv-install.
Executing: /lib/systemd/systemd-sysv-install enable programexample
The unit files have no installation config (WantedBy=, RequiredBy=, Also=,
Alias= settings in the [Install] section, and DefaultInstance= for template units). This means they are not meant to be enabled using systemctl.
Possible reasons for having this kind of units are:
• A unit may be statically enabled by being symlinked from another unit's
.wants/ or .requires/ directory.
• A unit's purpose may be to act as a helper for some other unit which has
a requirement dependency on it.
• A unit may be started when needed via activation (socket, path, timer,
D-Bus, udev, scripted systemctl call, ...).
• In case of template units, the unit is meant to be enabled with some
instance name specified.
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
28001 次 |
最近记录: |