'How to schedule a cron for the first Thursday of every month

I need to schedule a cron job to run at 3:00 PM on the first Thursday of every month. How can I do this? I have read another topic similar to this, but it is for the first Sunday of every month. How do I modify this to suit my needs? Please do not refer me to any manuals as they are of no help to me. This is why I am asking the question here.

Every first Sunday of very month

00 09 * * 7 [ $(date +\%d) -le 07 ] && /run/your/script

A simple answer should do here, I'm just don't know what the -le 07 stands for.

So the 4 is Thursday, What is the -le 07 in the cron?

is it a check for the first 7th day (Sunday) of the month?

00 15 * * 4 [ $(date +\%d) -le 07 ] && /run/your/script

Or should it be this one?

Assuming this would be a check for the first 4th Day (Thursday) of the month?

00 15 * * 4 [ $(date +\%d) -le 04 ] && /run/your/script

Since English isn't my mother tongue, I hope this is as clear as possible for you guys.

Thanks in advance.



Solution 1:[1]

the answer:

0 15 * * 4 [ $(date +\%d) -le 7 ] && command

the explanation:

First of all you need to realize that the first Thursday of the month will always have a day of the month that is in the set {1,2,3,4,5,6,7}. That is simply because there are only 7 days in a week. And thus the first Thursday cannot be have a day that is bigger then 7. The same holds evidently for any other weekday such as Tuesday or Saturday.

The command that cron will execute consists of two parts:

  • [ $(date "+\%d") -le 7 ]: This is a simple test that checks if the day of the month is smaller than 7. It essentially checks if we are in the first week of the month. The command date -d "+%d" returns the day of the month as a two-digit number (01,02,03,...,31) and is a string. The test command, here written in an alternative form with square brackets [ ... ] does a check to see if the integer comming from date is smaller then or equal to 7. You can read more on this when typing man test in a terminal.

  • command: this is the command that is going to be executed if the previous test is successful. I.e. if we are in the first week of the month. The reason why this will only execute if the test command is successful, is because of the &&. A command of the form cmd1 && cmd2 will execute cmd1 and only when that one is successful will it execute cmd2.

So since we now have the command, we can now build our crontab file. With a bit more comments (parts starting with #, you can write it as:

# Example of job definition:
# .---------------- minute (0 - 59)
# |  .------------- hour (0 - 23)
# |  |  .---------- day of month (1 - 31)
# |  |  |  .------- month (1 - 12) OR jan,feb,mar,apr ...
# |  |  |  |  .---- day of week (0 - 6) (Sunday=0 or 7)
# |  |  |  |  |
# *  *  *  *  *   command to be executed
  0  15 *  *  4   [ $(date +\%d) -le 07 ] && command

The above means, execute the above command at minute 0 of the 15th hour of any Thursday. And since the command contains the test for the first week, it will only run on the first Thursday of the month.

Solution 2:[2]

Why not simply use:

# Example of job definition:
# .---------------- minute (0 - 59)
# |   .------------- hour (0 - 23)
# |   |   .---------- day of month (1 - 31)
# |   |   |   .------- month (1 - 12) OR jan,feb,mar,apr ...
# |   |   |   |  .---- day of week (0 - 6) (Sunday=0 or 7)
# |   |   |   |  |
# *   *   *   *  *   command to be executed
  0  15  1-7  *  4   command

So you tell cron to run at minute 0, hour 15, first 7 days of the mounth, on 4th day (Thursday). It will for sure include only one Thursday, the first one, because in 7 consecutive days of a month it will be for sure only one Thursday and in 7 consecutive days cannot be 2 Thursdays.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Silviu Ionu? CHINGARU