1838571 Members
3411 Online
110128 Solutions
New Discussion

Self monitoring scripts

 
SOLVED
Go to solution
Dermot Beirne
Frequent Advisor

Self monitoring scripts

Hi,
I am writing a script that will take different lenghts of time to complete, depending on certain conditions. I want to have this script running at predefined short intervals in cron. If an instance of the script is still running when a second one starts, it will cause me problems. I know I can run the script once, and have a sleep line in it and not use cron, but this does not suit my requirements, so I want to know how to reliably get a script to check if it is already running before starting. I also know that i could create a tmp file when the script starts and check for this files existance each time it runs, but this also has some drawbacks for my scenario. Any ideas? Thanks in advance.
Dermot
Happy is harder than money. Anyone who thinks money will make them happy, doesn't have money.
6 REPLIES 6
ian Dennison
Regular Advisor

Re: Self monitoring scripts

I did this a year or so ago,..

# Broken down into a copuple of statements,...

export CPID=$$
ps -ef |grep [script name] |grep -v grep >/tmp/file1

cat file1 |awk -v cpid=$CPID '$2 != cpid && $3 != cpid { print $0 }' >/tmp/file2

# File /tmp/file2 now contains versions of script name running that are not the current script (CPID in column 2 of ps -ef)
# nor spawned by the current script (CPID in column 2 of ps -ef).
#

Share and Enjoy! Ian
Lets do it to them before they do it to us! www.fred.net.nz
Eric Ladner
Trusted Contributor

Re: Self monitoring scripts

Another thing to try is to create a "lock file".

When the script starts up, it checks to see if the lock file exists, if not, it creates it and does it's thing. If it does exist, it can either wait and check every minute or so until it goes away then continues on, or it can abort, your choice.

The last thing the program does before it leaves is removes the file.

Here's an example that aborts if it's already running.

-------------
LOCKFILE=/var/tmp/whatever

function clean_exit()
{
rm -f $LOCKFILE
exit
}
# Clean exit, even if killed, Ctrl-C'd etc.
trap clean_exit HUP INT QUIT TERM

#Check the lockfile. You can loop here if
#you want to wait and start when the other
#job goes away
if [ -f $LOCKFILE ]; then
exit
fi

#Create the lockfile
touch $LOCKFILE

# Do some stuff here.. Any time you need to
# get out of the script, call clean_exit
# instead of return or exit

# Clean up before we leave
clean_exit

Volker Borowski
Honored Contributor

Re: Self monitoring scripts

Hi,

another option might be not to use cron but "at" instead, and let the script reschedule itself at the end.

Or let it run in an endless loop interupted by "sleep xxx" all the time.

Problem is, when the script dies, it will never run again, but it will not do this with the "lock-file" solution as well, because it is not unlocking itself.

No solution either, if the script hangs.

Any more details?
Volker
BFA6
Respected Contributor

Re: Self monitoring scripts

Hi,

I also have scripts that run from cron at 10 min intervals, and it all goes horribly wrong if 2 run at the same time.
I used the "lock file" method suggested previously. The first thing the script does is check for the existence of the lock file - if present script exits. The last thing the script does is remove the lock file.

regards,

Hilary
harry d brown jr
Honored Contributor
Solution

Re: Self monitoring scripts

Dermot,

try this:


#!/usr/bin/ksh
#
# using "lsof" test to see what other processes are using this same
# script name (be careful if script names are the same but in different
# directories - ie /usr/bin/stupid vs /usr/local/bin/stupid)
#
# using "terse" option of "lsof" return PID's that have this script
# open ($0) and then cound the number of "words", where each word is
# a PID, so if two scripts were using this script then the second script
# to run would return a 2 for two PID's
#
HOWMANYUSERS=`/usr/local/bin/lsof -t $0|wc -l`
if [ "$HOWMANYUSERS" = "1" ]
then
#
# test again to make sure there were no "sneaks"
# sleep 1 second to ensure
#
sleep 1
HOWMANYUSERS=`/usr/local/bin/lsof -t $0|wc -l`
if [ "$HOWMANYUSERS" = "1" ]
then
echo "safe to execute"
else
echo "crazy man walking - need to exit"
fi
else
echo "crazy man walking - need to exit"
fi
#
# add a sleep here, like
# sleep 30
# to test this script, but
# remember to add a "&" at the end of the command line so
# so you can test what happens if you run it a few times in
# a row: /tmp/scriptname &
#
# --normal code here---
#


live free or die
Live Free or Die
Eric Buckner
Regular Advisor

Re: Self monitoring scripts

Or you can just do this:

if [ `ps -ef | grep $0 | grep -v grep | wc -l` -eq 1]; then

this is running already

fi


Eric
Time is not a test of the truth.