仅在 Linux 中 Cron 作业未运行时运行 Cron 作业


介绍

Cron 是 Linux 中的一个实用程序,允许用户计划命令或脚本在特定的日期和时间自动运行。但是,有时可能需要确保 cron 作业一次只运行一次。在本文中,我们将讨论两种防止 cron 任务重叠的方法:使用进程跟踪和使用“.pid”文件。

通过进程查找正在运行的实例

避免 cron 任务运行重叠的一种方法是在运行它之前检查任务进程是否存在。这可以使用pgrep命令完成,该命令允许我们搜索具有特定名称的进程并查看其进程 ID。如果找到该进程,则表示该任务已在运行,并且不应该运行新实例。

要使用此方法,我们可以修改 cron 任务以在开头包含以下命令:

if pgrep -x "script_name" > /dev/null ; then
   exit 0
fi

在上面的命令中,“script_name”是要作为 cron 作业运行的脚本或命令的名称。“-x”选项告诉pgrep匹配确切的进程名称,“> /dev/null”部分将输出重定向到空,以便它不会弄乱终端。如果脚本已在运行,则 if 语句将为真,并且新实例将关闭而不会运行。

例如,如果我们有一个名为“my_script.sh”的脚本,我们想将其作为 cron 作业运行,我们可以修改 cron 作业以包含以下命令:

if pgrep -x "my_script.sh" > /dev/null ; then
   exit 0
fi

这将在运行 cron 任务之前检查“my_script.sh”进程是否存在。如果找到该进程,则新的任务实例将不会运行。

使用 .pid 文件

避免 cron 任务执行重叠的另一种方法是使用“.pid”文件。.pid 文件是一个简单的文本文件,其中包含正在运行的进程的进程 ID。当任务运行时,它会创建一个“.pid”文件,其中包含该任务的进程 ID。如果 .pid 文件已存在,则表示该任务已在运行,并且不应该运行新实例。

要使用此方法,我们可以修改 cron 任务以在开始时包含以下命令:

pid_file="/path/to/pid/file/task.pid"
if [ -f "$pid_file" ] && kill -0 $(cat "$pid_file") 2>/dev/null; then
    exit 0
fi
echo $$ > "$pid_file"

在上面的命令中,“pid_file”是 .pid 文件的路径,它应该是运行 cron 任务的用户可写的路径。if 语句首先检查 .pid 文件是否存在,然后使用 kill 命令向 .pid 文件中包含的进程 ID 发送信号。“-0”选项告诉 kill 发送空信号,该信号实际上不会杀死进程,但允许我们检查进程是否仍在运行。如果进程仍在运行,则信号将成功传递,并且 if 语句将为真,这将导致新实例退出而不会被执行。如果进程未运行,则信号将不会传递,并且 if 语句将为假,允许任务运行。

if 语句的第二行“2>/dev/null”将所有错误消息重定向到空,因此它们不会弄乱终端。

任务运行完成后,必须删除 .pid 文件以允许任务的未来实例运行。这可以使用以下命令完成:

$ rm "$pid_file"

例如,如果我们有一个名为“my_script.sh”的脚本,我们想将其作为 cron 作业运行,并且我们想将 .pid 文件存储在“/tmp”目录中,我们可以修改 cron 作业以包含以下命令:

pid_file="/tmp/my_script.pid"
if [ -f "$pid_file" ] && kill -0 $(cat "$pid_file") 2>/dev/null; then
   exit 0
fi
echo $$ > "$pid_file"

这将在“/tmp”目录中创建一个名为“my_script.pid”的“.pid”文件,并在其中存储正在运行的任务的进程 ID。如果“.pid”文件已存在,则表示该任务已在运行,并且新的实例将不会运行。任务运行完成后,“.pid”文件将被删除,从而允许任务的未来实例运行。

结论

在本文中,我们讨论了两种防止 cron 任务重叠执行的方法。第一种方法是使用进程发现来检查活动进程是否存在,然后再执行活动,第二种方法是使用“.pid”文件来存储正在运行的活动进程 ID。这两种方法都可以用于确保 cron 任务一次不会运行多次,这在任务资源密集型或需要一次只运行一次的情况下非常有用。需要注意的是,这两种方法都需要更改任务脚本本身,并且可能不适用于所有类型的任务。但是,它们可以是确保 cron 任务正确运行的有用工具。

更新于:2023年1月25日

2K+ 浏览量

开启你的 职业生涯

通过完成课程获得认证

开始
广告