Operating System - HP-UX
1820638 Members
1951 Online
109626 Solutions
New Discussion юеВ

run crontab at last day of month

 
SOLVED
Go to solution
ust3
Regular Advisor

run crontab at last day of month

If I want to set the crontab job to run at last day of every month ( may be 28th, 29th 30th or 31th ) , if I set * * 31 * * , it will run at 31th of month, but it is not the last day of Feb. , can advise what can I do ? thx
14 REPLIES 14
A. Clay Stephenson
Acclaimed Contributor
Solution

Re: run crontab at last day of month

First detach the attached script, caljd.sh, and copy it to /usr/local/bin and make it executable. Next, set your cron job to run on the 28th-31st and let the job itself determine if this is the last day of the month. If so then pperform your task else exit and do nothing.

---------------------------------
#!/usr/bin/sh

export PATH=${PATH}:/usr/local/bin
typeset -i STAT=0
if [[ $(caljd.sh -M) != $(caljd.sh -M -n 1) ]]
then
echo "It's the last day of the month; do your thing"
STAT=${?}
fi
exit ${STAT}
-----------------------------------------

Essentially, this compares the month of today with the month of tomorrow and if they differ, it's the last day of the month. Caljd.sh will work on leap years and across year boundaries. Invoke as caljd.sh -u for full usage and many examples.


If it ain't broke, I can fix that.
Dennis Handly
Acclaimed Contributor

Re: run crontab at last day of month

Other than Clay's clever trick, you could hardcode 3 crontab entries with the same command, one for Feb 28,29; one for 30 and the last for 31 day months. And for Feb 28, you need to check for leap years.
Hein van den Heuvel
Honored Contributor

Re: run crontab at last day of month


And much similar you could execute in that script this perl one-liner:

#perl -e 'exit ((localtime)[4] != (localtime(time+86400))[4])'

Next test $?

If it is 1 then it is the last day as the month now (4th element in tm array) was not equal to the month for the time now + a day worth of seconds.

If it is 0 then exit and wait for re-run.

fwiw,
Hein.


Wim Rombauts
Honored Contributor

Re: run crontab at last day of month

Another solution for when you run your cron-job on days 28-31, start the script with

if [ "$(TZ=GMT-24 ; date +\%d)" = "01" ]
then
execute-script
fi
James R. Ferguson
Acclaimed Contributor

Re: run crontab at last day of month

Hi:

You can also leverage the 'cal' utility. To find the last day of the current month simply do:

DAY=$(cal|awk 'END{print DAY};{if (NF<1) {next};DAY=$NF}')

if [ ${DAY} -eq $(date +%m) ]; then
echo "end-of-month"
else
echo "not last day"
fi

Regards!

...JRF...
Arturo Galbiati
Esteemed Contributor

Re: run crontab at last day of month

Hi,
why not use the old but good cal?

HH MM * * * [[ $(cal) = *$(date +%d) ]] && /path/to/script


HTH,
Art
Dennis Handly
Acclaimed Contributor

Re: run crontab at last day of month

>Art: why not use the old but good cal?
[[ $(cal) = *$(date +%d) ]]

Pretty clever!
Arturo Galbiati
Esteemed Contributor

Re: run crontab at last day of month

Thx Dennis.
Sometimes we are searching very complex solution while an easy UNIX command is available.
My mentor always said me: RTFM!

Rgds,
Art
Ben Dehner
Trusted Contributor

Re: run crontab at last day of month

Or, for the truly lazy like me, schedule that cron job to run at 00:01 on the FIRST day of the month. I've found this is usually adequate.
Trust me, I know what I'm doing
Sandman!
Honored Contributor

Re: run crontab at last day of month

>> HH MM * * * [[ $(cal) = *$(date +%d) ]] && /path/to/script <<

Ingenious work indeed Art!!!
Would help if you would enlighten the likes of me on its usage.
Bob E Campbell
Honored Contributor

Re: run crontab at last day of month

Lots of solutions, but hats off to Arturo for that one. I was sure that the embedded newlines would block that until I saw it myself.
Dennis Handly
Acclaimed Contributor

Re: run crontab at last day of month

>Sandman: Would help if you would enlighten the likes of me on its usage.

If you look at it, it is pretty obvious. ;-)
[[ $(cal) = *$(date +%d) ]]

Take the output from cal(1) and do a pattern match. Make sure that it matches the pattern "*current-day". The only time the current day matches the end of the line is the last day of the month. (Or if you have an evil locale, with one digit day of month, the 1st, or 8th and 9th for Feb.)-:

To fix that, use $(date +%2d)

>Bob: I was sure that the embedded newlines would block that

I'm not sure there are any when you use $().
Using the following shows them replaced by whitespace:
$ echo $(cal) > file

>Ben: schedule that cron job to run at 00:01 on the FIRST day of the month. I've found this is usually adequate.

I was going to suggest something similar but the process may need to be done in the middle of the day.
A. Clay Stephenson
Acclaimed Contributor

Re: run crontab at last day of month

... and the other reason that doing something during the first minute of the next month may not be a good idea is that you may need to generate reports for what is now the previous month so that you just turned the tedious date calculations around so that you have to compute the previous day.

... and often what is really meant by the "last day of the month" is really the last working day of the month (ie not a weekend and not a holiday) which becomes just a few extra arguments for caljd.sh.

if [[ $(caljd.sh -M) -ne $(caljd.sh -n 1 -x 6 -x 0 -h -M) ]]
then
echo "Today's the last working day of the month."
fi
If it ain't broke, I can fix that.
Victor Fridyev
Honored Contributor

Re: run crontab at last day of month

Hi,

First of all, I don't see any real reason not move all "last-day-of-a-month" jobs to the first day of a month, I fully agree with Ben Dehner here.
BTW, it seems, some of Olimpians in a similar previous thread proposed the following trick:

argus:/# (date; export TZ=GMT-24 ; date)
Sat Sep 22 11:44:53 IST 2007
Sun Sep 23 09:44:53 GMT 2007

You can play with TZ expression in date +%m command and compare it's output:

if [ $(date +%m) -ne $(export TZ=GMT-24 ; date +%m)]; then
echo "This is the last day of the month
fi


HTH
Entities are not to be multiplied beyond necessity - RTFM