仅当 cron 任务尚未运行时才运行

2024-11-05 08:37:00
admin
原创
30
摘要:问题描述:我正在尝试设置一个 cron 作业作为我创建的守护进程的看门狗。如果守护进程出错并失败,我希望 cron 作业定期重新启动它...我不确定这有多大可能,但我读过几个 cron 教程,找不到任何可以满足我要求的东西...我的守护进程是从 shell 脚本启动的,所以我实际上只是在寻找一种方法来运行 c...

问题描述:

我正在尝试设置一个 cron 作业作为我创建的守护进程的看门狗。如果守护进程出错并失败,我希望 cron 作业定期重新启动它...我不确定这有多大可能,但我读过几个 cron 教程,找不到任何可以满足我要求的东西...

我的守护进程是从 shell 脚本启动的,所以我实际上只是在寻找一种方法来运行 cron 作业,仅当该作业的上一次运行尚未运行时。

我发现这篇文章确实为我尝试使用锁文件执行的操作提供了解决方案,但我不确定是否有更好的方法来做到这一点......


解决方案 1:

使用flock。它是新的。它更好。

现在您不必自己编写代码。在此处查看更多原因: https: //serverfault.com/a/82863

/usr/bin/flock -n /tmp/my.lockfile /usr/local/bin/my_script

解决方案 2:

我为自己编写的打印后台处理程序执行了此操作,它只是一个 shell 脚本:

#!/bin/sh
if ps -ef | grep -v grep | grep doctype.php ; then
        exit 0
else
        /home/user/bin/doctype.php >> /home/user/bin/spooler.log &
        #mailing program
        /home/user/bin/simplemail.php "Print spooler was not running...  Restarted." 
        exit 0
fi

它每两分钟运行一次,非常有效。如果由于某种原因进程没有运行,我会让它通过电子邮件向我发送特殊信息。

解决方案 3:

正如其他人所说,编写和检查 PID 文件是一个很好的解决方案。这是我的 bash 实现:

#!/bin/bash

mkdir -p "$HOME/tmp"
PIDFILE="$HOME/tmp/myprogram.pid"

if [ -e "${PIDFILE}" ] && (ps -u $(whoami) -opid= |
                           grep -P "^s*$(cat ${PIDFILE})$" &> /dev/null); then
  echo "Already running."
  exit 99
fi

/path/to/myprogram > $HOME/tmp/myprogram.log &

echo $! > "${PIDFILE}"
chmod 644 "${PIDFILE}"

解决方案 4:

令人惊讶的是没有人提到run-one。我已经用这个解决了我的问题。

 apt-get install run-one

run-one然后在 crontab 脚本前添加

*/20 * * * * * run-one python /script/to/run/awesome.py

查看这个askubuntu SE 答案。您也可以在那里找到详细信息的链接。

解决方案 5:

不要尝试通过 cron 来执行此操作。无论如何,让 cron 运行一个脚本,然后让脚本决定程序是否正在运行,并在必要时启动它(请注意,您可以使用 Ruby 或 Python 或您最喜欢的脚本语言来执行此操作)

解决方案 6:

我在运行 php 脚本时执行的方式是:

crontab:

* * * * * php /path/to/php/script.php &

PHP代码:

<?php
if (shell_exec('ps aux | grep ' . __FILE__ . ' | wc  -l') > 1) {
    exit('already running...');
}
// do stuff

此命令在系统进程列表中搜索当前 php 文件名,如果存在,则行计数器(wc -l)将大于一,因为搜索命令本身包含文件名

因此如果您运行 php cron,请将上述代码添加到 php 代码的开头,它将只运行一次。

解决方案 7:

您也可以直接在 crontab 中将其作为一行程序执行:

* * * * * [ `ps -ef|grep -v grep|grep <command>` -eq 0 ] && <command>

解决方案 8:

作为对 Earlz 回答的后续,您需要一个包装器脚本,该脚本在启动时创建一个 $PID.running 文件,并在结束时删除。包装器脚本调用您想要运行的脚本。包装器是必需的,以防目标脚本失败或出错,pid 文件会被删除。

解决方案 9:

lockrun不需要为您的 cron 作业编写包装脚本。http ://www.unixwiz.net/tools/lockrun.html

解决方案 10:

# one instance only (works unless your cmd has 'grep' in it)
ALREADY_RUNNING_EXIT_STATUS=0
bn=`basename $0`
proc=`ps -ef | grep -v grep | grep "$bn" | grep -v " $$ "`
[ $? -eq 0 ] && {
    pid=`echo $proc | awk '{print $2}'`
    echo "$bn already running with pid $pid"
    exit $ALREADY_RUNNING_EXIT_STATUS
}

更新..使用flock的更好方法:

/usr/bin/flock -n /tmp/your-app.lock /path/your-app args 

解决方案 11:

我建议使用现有的工具,例如monit ,它将监视并自动重启进程。这里有更多信息。它应该在大多数发行版中都很容易获得。

解决方案 12:

这个从来没有让我失望过:

one.sh

LFILE=/tmp/one-`echo "$@" | md5sum | cut -d  -f1`.pid
if [ -e ${LFILE} ] && kill -0 `cat ${LFILE}`; then
   exit
fi

trap "rm -f ${LFILE}; exit" INT TERM EXIT
echo $$ > ${LFILE}

$@

rm -f ${LFILE}

计划任务

* * * * * /path/to/one.sh <command>

解决方案 13:

文档:https://github.com/timkay/solo

solo 是一个非常简单的脚本(10 行),可防止程序一次运行多个副本。它与 cron 配合使用,可确保在前一个作业完成之前不会运行下一个作业。

例子

* * * * * solo -port=3801 ./job.pl blah blah

解决方案 14:

我建议对rsanden 的回答进行以下改进(我会以评论的形式发布,但声誉不够……):

#!/usr/bin/env bash

PIDFILE="$HOME/tmp/myprogram.pid"

if [ -e "${PIDFILE}" ] && (ps -p $(cat ${PIDFILE}) > /dev/null); then
  echo "Already running."
  exit 99
fi

/path/to/myprogram

这避免了可能的错误匹配(以及 grepping 的开销),并且它抑制输出并仅依赖于 ps 的退出状态。

解决方案 15:

简单的自定义 php 就足以实现。无需与 shell 脚本混淆。

假设你想运行php /home/mypath/example.php如果没有运行

然后使用以下自定义 php 脚本来完成相同的工作。

创建以下/home/mypath/forever.php

<?php
    $cmd = $argv[1];
    $grep = "ps -ef | grep '".$cmd."'";
    exec($grep,$out);
    if(count($out)<5){
        $cmd .= ' > /dev/null 2>/dev/null &';
        exec($cmd,$out);
        print_r($out);
    }
?>

然后在你的 cron 中添加以下内容

* * * * * php /home/mypath/forever.php 'php /home/mypath/example.php'

解决方案 16:

如果你要走这条路,请考虑使用 pgrep(如果可用)而不是通过 grep 管道传输的 ps。不过,就我个人而言,我从以下形式的脚本中获得了很大的收益

while(1){
  call script_that_must_run
  sleep 5
}

虽然这可能会失败,但 cron 任务通常处理重要事务的最佳方式。这只是另一种选择。

相关推荐
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   601  
  华为IPD与传统研发模式的8大差异在快速变化的商业环境中,产品研发模式的选择直接决定了企业的市场响应速度和竞争力。华为作为全球领先的通信技术解决方案供应商,其成功在很大程度上得益于对产品研发模式的持续创新。华为引入并深度定制的集成产品开发(IPD)体系,相较于传统的研发模式,展现出了显著的差异和优势。本文将详细探讨华为...
IPD流程是谁发明的   7  
  如何通过IPD流程缩短产品上市时间?在快速变化的市场环境中,产品上市时间成为企业竞争力的关键因素之一。集成产品开发(IPD, Integrated Product Development)作为一种先进的产品研发管理方法,通过其结构化的流程设计和跨部门协作机制,显著缩短了产品上市时间,提高了市场响应速度。本文将深入探讨如...
华为IPD流程   9  
  在项目管理领域,IPD(Integrated Product Development,集成产品开发)流程图是连接创意、设计与市场成功的桥梁。它不仅是一个视觉工具,更是一种战略思维方式的体现,帮助团队高效协同,确保产品按时、按质、按量推向市场。尽管IPD流程图可能初看之下显得错综复杂,但只需掌握几个关键点,你便能轻松驾驭...
IPD开发流程管理   8  
  在项目管理领域,集成产品开发(IPD)流程被视为提升产品上市速度、增强团队协作与创新能力的重要工具。然而,尽管IPD流程拥有诸多优势,其实施过程中仍可能遭遇多种挑战,导致项目失败。本文旨在深入探讨八个常见的IPD流程失败原因,并提出相应的解决方法,以帮助项目管理者规避风险,确保项目成功。缺乏明确的项目目标与战略对齐IP...
IPD流程图   8  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用