如何将Bash脚本作为守护进程运行?
有时,我们需要运行自动化流程,为此,我们使用一个在后台持续运行的脚本。在Linux中,这类脚本被称为“守护进程”。这些守护进程允许我们独立于终端会话运行。这意味着即使我们关闭会话,脚本也会继续运行。
在本教程中,我们将学习如何**将Bash脚本转换为守护进程**。
什么是守护进程?
守护进程只是一个在后台持续运行的程序或进程,无需用户交互。在您日常的Linux任务中,您可能已经使用过一些这样的进程。例如,如果您使用像MySQL或Postgres这样的数据库,它们就有这样的服务。
例如,要启动Postgres,您可以说service Postgres start。此命令的作用是在后台运行一个服务(守护进程)来启动数据库,并且它会一直运行直到您停止它。这是一个守护进程的真实示例。
**系统需要守护进程在后台运行一些服务和任务**。要查看系统中正在运行的所有守护进程,请运行以下命令:
ps axl
这将列出系统中所有正在运行的守护进程。
将Bash脚本作为守护进程运行
Bash脚本是一种强大的脚本语言,允许我们自动化任务,而使用守护进程可以为我们带来更多好处,例如自动化重复性任务并确保我们的脚本在后台持续运行。这还允许我们专注于其他任务,因为我们的守护进程与会话分离。
让我们一起学习将简单的Bash脚本转换为守护进程的步骤和方法。
首先,让我们创建一个简单的Bash脚本文件,例如:
#!/bin/bash i=0 while true; do echo "Running ... $i" ((i++)) sleep 10 done
我们创建一个示例,它每10秒打印一次“正在运行...”消息,并每次递增变量i。
终端会话
当我们使用终端会话时,如果我们关闭终端窗口(会话),则此会话中的所有进程都将被杀死。例如,如果您运行这样的进程:
sleep 300 &
这将在后台运行**sleep**命令,您可以使用**jobs**命令查看后台运行的进程。但是,如果您关闭终端并再次打开它,您会看到该进程已被杀死,因为它附加到当前的shell会话。您可以使用**pstree**命令检查这一点,该命令显示进程的父进程。例如:
pstree -s 6542
在这里,我们将进程ID传递给**pstree**,它将显示如下输出:
systemd───systemd───gnome-terminal───bash───sleep
在这种情况下,**sleep**命令的父进程是**bash**,而**bash**的父进程是终端本身,在我的例子中是**gnome-terminal**。
使用nohup创建守护进程
为了将脚本或进程转换为守护进程,我们将使用一个名为**nohup**的工具,它代表“no hang up”(不挂起)。此命令采用如下选项:
nohup path/script.sh > /dev/null 2>&1 &
让我们解释一下它的作用:
- **path/script** - 我们需要转换为守护进程的文件。
- **/dev/null 2>$1** - 将所有输出重定向到/dev/null,防止脚本阻塞。
- **&** - 这将使脚本在后台运行。
使用Systemd
我们可以使用systemd(几乎所有发行版中都可用的系统和服务管理器)来更好地控制您的守护进程。
为此,请在** /etc/systemd/myexample.service** 位置创建一个服务单元文件:
[Unit] Description=My Script Daemon [Service] ExecStart=/path_to_script.sh Restart=always User=root StandardOutput=null StandardError=null [Install] WantedBy=multi-user.target
这将使我们更好地控制守护进程。
要启用并启动服务,我们使用以下命令:
sudo systemctl enable myexample.service sudo systemctl start myexample.service
管理守护进程
使用**systemd**将为我们提供一些管理服务(守护进程)的命令。
要启动守护进程,请使用以下命令:
sudo systemctl start myexample.service
要停止守护进程,请使用以下命令:
sudo systemctl stop myexample.service
您可以使用以下命令检查守护进程的状态:
sudo systemctl stop myexample.service
结论
在本教程中,我们讨论了如何将简单的Bash脚本转换为守护进程。我们使用了两种方法:一种是使用**nohup**命令的简单方法,另一种是使用**systemd**来更好地控制守护进程。