XKCD… (Though I’m not sure Randall has a
completely accurate understanding of the MAILTO variable which
according to my reading of
man cron is for addresses and not mail
box directories. I could be the wrong one, but no thanks to the man
page. This might be a difference of old school Vixie cron and newer
cronie. See below.)
Vixie vs. Cronie
In the ancient times, a clever guy named Paul Vixie created cron and
it was called cron. And that was fine. But then a lot happened and
Paul had better things to do with his time (apparently) than mess
about with cron. So some different people reimplemented it. Tons of
them really, but the one that seems to be emerging as the best one to
use for practical purpose is
Cronie. Switching to this seems
to cure the Gentoo braindead problem of new vixie-cron crontab edits
not taking effect without a complete process restart. I think I’m one
of the last people to actually use ancient
because I have been using it since ancient times and I didn’t know
that it had been cast into the obscurity void.
Cron uses a "crontab" which is a list of rules for what should happen when. To edit these rules use this command which will properly lock the file and invoke your editor:
To see what is in your crontab use:
Here is a prototypical crontab.
MAILTOfirstname.lastname@example.org SHELL=/bin/bash # Here is a sample cron tab that explains what goes where. # Basically, don't put a * in the first two fields unless you # want a LOT of action. # # minute # | hour(0-23) # | | day of month(1-31) # | | | month of year(1-12 or jan, Feb, mAR, etc) # | | | | day of week(0-6 (0=Sun), or mon, tUE, Wed, etc.) # | | | | | COMMANDS # 0 2 * * 0,4 /sbin/something # */2 means activate when TIME_UNIT MOD 2 == 0 # Normal style of entries. 30 * * * * /home/xed/somegood_hourly_script >/dev/null 2>&1 55 8 * * * /home/xed/somegood_daily_script # Anniversary reminder example. 0 0 15 4 * echo "File your taxes yet?" # Example alarm. 30,42 14 * * 1,2,4,5 /usr/bin/play -q /home/xed/collection/sounds/cattle.wav # Check if drive is full. If not, ignore. If it is, send email. 22 3 * * 0 df | grep "100. /"
Difficult Things To Specifiy
First you can test to make sure your system can use this technique.
* * * * * expr `date +\%M` \% 2 >>/dev/null || date >> ~/testdir/2weekcronttest
This produces something like:
Tue Sep 25 12:40:01 PDT 2012 Tue Sep 25 12:42:01 PDT 2012 Tue Sep 25 12:44:01 PDT 2012 Tue Sep 25 12:46:01 PDT 2012
If you want odd numbered minutes or weeks or whatever, use something like this:
* * * * * expr \( `date +\%M` + 1 \) \% 2 >>/dev/null || date >> ~/testdir/2weekcronttest
This isn’t too exciting since you can get every other minute by doing
*/2 in the minute field. But it quickly proves the idea which will
also work on weeks where the normal syntax breaks down.
If the test works out, then you can see that replacing the
%W will give you a cron job that runs on every even (or odd) week of
the year. If the test doesn’t work, see the section on percents below.
Here’s a cron rule that runs biweekly (fortnightly):
0 11 * * thu expr `date +\%W` \% 2 >>/dev/null || /usr/local/bin/indexthedb
First note the "MAILTO=" line which will take all standard output of the commands run by cron and send them to that specified email address.
Mail is generally a separate problem from cron and to make sure automatic notifications work, make sure that manual mail sending is good to go.
cal 2000 | mail -a "From: raven back-upper <email@example.com" \ -s "subject goes here" firstname.lastname@example.org
Make sure you have
ssmtp installed (Gentoo anyway) and
If this works as planned then you can specify some mailing jobs in cron. That would look something like:
0 0 * * 0 echo "Weekly Backup Reminder" | /usr/bin/mail \ -a "From: $(hostname) <email@example.com>" \ -s "Cron testing from sad" firstname.lastname@example.org
You can try
\ but I just put them here for illustration. Normally
I’d just have all this on one line to be safe.
In crontabs, "%" delimits the command’s standard input (the first percent) or signifies a new line within that input. The only use I can imagine for this is mailing things.
55 * * * * mail -a "From: Crontest <email@example.com>" -s "A Test Of Cron" xed@blackswan%This is a test.%This should be line 2 of the message.
This is helpful when you want cron to just send you reminder notes. I find, however, that pipes work just fine making this percent functionality more of a nuisance than anything.
It is theoretically possible to escape this behavior with a backslash
\% but I’ve had trouble getting that to work sometimes.
Another way to get a real "%" without including it on the command line
is to use
$'\x25' which is a bit complex but mostly works without
messing up other things. This is a Bash substitution and it’s
important to note that the vixie-cron daemon sets the
SHELL value to
/bin/sh by default. But you can add a line with
that this kind of fancier substitution does work. Of course this may
mess up other things.
Definitely test your entry before relying on it if it includes "%".
For some reason, changes made on some Gentoo systems with
crontab -e are not
taking effect. The vixie-cron daemon must be restarted:
$ sudo /etc/init.d/vixie-cron restart
I don’t know why that is but it’s wise to check to make sure that cron does what you think it’s supposed to be doing.
See my aforementioned remarks about Cronie as perhaps a better choice.
at is the lesser known little brother of
at command is
cron in that it schedules jobs to be run at a later time,
at specifies a single fixed future point in time for the job to
run as opposed to periodically.
* …has a daemon process (
atd) similar to
crond to manage jobs.
* …is for jobs set to run at specific times, not periodically (like
* …can also schedule jobs for when the cpu is unloaded.
* …can email you when the job is complete.
* …preserves environment it was run from (cron does not).
Here are some simple examples. This is a very normal kind or thing:
echo '/home/xed/mknewyearbackups.sh 2014' | at midnight January 1 2014
I’m actually not sure if
midnight is after the day specified or
before. Need to check that.
Here is a good way to get rid of temp files:
$ echo "rm /tmp/mytempfile" | at now + 10 minutes
batchis an alias of
atwhich runs jobs when the CPU load is low.
man atfor all the details.
Also this web page is useful (it can be hard to search for good info on
at can use
/etc/at.deny. It may be smart to
make these as symlinks to