Using rsnapshot with systemd
rsnapshot nicely illustrates some of the features of systemd timers. As of Ubuntu 16.04, the rsnapshot package doesn't ship with systemd service and timer files, so you have to set them up yourself.
Before I show how to setup rsnapshot with systemd
, I want to cover some of the benefits of using systemd
timers instead of cron.
Cron syntax vs systemd timer syntax
systemd
timer has a syntax for specifying repeating events than the old cron syntax.
Here's how to specify a "weekly" cron job at 3 AM with the old cron syntax:
# cron syntax
0 3 * * 1
Here's the same thing expressed in a systemd
timer file:
*-*-* 00:03:00
If you correctly guess that the right side in the systemd format represents Hour:Minute:Day, then you are well on your way to correctly guessing that the left side represents 'Year-Month-Day' format.
The old cron syntax looks nothing like a date and has to be memorized.
Logging and notification
A traditional well-behaved cron job produces no output unless there is an error, in which case the output will be mailed to you.
Because rsnapshot
runs an important backup job, it's useful to have some detailed output about what it did, even on successful runs.
With systemd, output is sent to the systemd journal by default. You don't hav to set up any output redirection or log rotation just to have good logging. Once set up, you can get logs for any of your rsnapshot runs with syntax like this:
journalctl -u rsnapshot@daily
If your login use in the systemd-journald
group, you also don't have to be root just to check out the logs. You can still get a nicely formatted email if rsnapshot fails. More on that below.
Easy status reporting
systemd
makes it easy to check on the status of your cron job. When did it run last? Was the last run a success or a failure? What were the most recent logs?. All those questions can answered with a quick check of the status
command:
systemctl status rsnapshot@daily
You don't have to root to check that either.
Configuring systemd unit files for snapshot
Disable cron files
To avoid conflict, make sure you disable running rsnapshot via cron in /etc/cron.d/rsnapshot
One time Setup: email-on-failure
In Ubuntu 16.04, there's a not a built-in solution for getting email-on-mail when using systemd timers instead of cron. This is the one drawback I've found. However, once you set this up, you can re-use the solution for all your other systemd timers.
The following assumes you've already got outgoing email working on your box.
First, install a script which will mail diagnostic output for a failed systemd service ((more context](://bugs.launchpad.net/ubuntu/+source/systemd-cron/+bug/1583743)):
sudo wget -O /usr/local/bin/mail_on_failure https://raw.githubusercontent.com/systemd-cron/systemd-cron/master/src/bin/mail_on_failure.py
Next, install a service file that will be used to call this scirpt when another service fails. Name it like: /etc/systemd/system/status-email-admin@.service
The contents would be:
[Unit]
Description=status email for %I to admin
[Service]
Type=oneshot
ExecStart=/usr/local/bin/mail_on_failure %i
User=nobody
Group=systemd-journal
Now for any service file that you want to send mail-on-failure, you'll include these bits in your systemd .service
file:
[Unit]
# Like Cron would, send devops an email if this fails
OnFailure=status-email-admin@%n.service
[Service]
Environment="MAILTO=admin@example.com"
As you would for cron, you can customize the MAILTO environment variable to suit your needs for each service file.
rsnapshot systemd service file
Using a systemd
template file, a single file can be used to configure rsnapshot
runs for daily
, weekly
and monthly
.
Create /etc/systemd/system/rsnapshot@.service
with the following contents.
[Unit]
Description=rsnapshot (%I) backup
# Like Cron would, send an email if this fails
OnFailure=status-email-admin@%n.service
[Service]
Environment="MAILTO=admin@rideamigos.com"
Type=oneshot
Nice=19
IOSchedulingClass=3
ExecStart=/usr/bin/rsnapshot %I
Creating rsnapshot timer files
Now you can create timers for the daily, weekly, monthly rsnapshot runs. In the example files I've set the daily
task to run at 5:30 AM, the weekly task at 4:30 AM and the monthly task at 3:30 AM. Adjust to suit.
/etc/systemd/systemm/rsnapshot-daily.timer
[Unit]
Description=rsnapshot daily backup
[Timer]
# Run every day at 5:30 AM local time
OnCalendar=05:30
Persistent=true
Unit=rsnapshot@daily.service
[Install]
WantedBy=timers.target
/etc/systemd/systemm/rsnapshot-monthly.timer
[Unit]
Description=rsnapshot monthly backup
[Timer]
# Run once per month at 3:30 local time, before daily and weekly runs
OnCalendar=*-*-1 03:30:00
Persistent=true
Unit=rsnapshot@monthly.service
[Install]
WantedBy=timers.target
/etc/systemd/systemm/rsnapshot-weekly.timer
[Unit]
Description=rsnapshot weekly backup
[Timer]
# Run once per week on Monday at 4:30 local time, before daily
OnCalendar=Monday *-*-* 04:30:00
Persistent=true
Unit=rsnapshot@weekly.service
[Install]
WantedBy=timers.target
Enabling timers
Finally, you can enable the timer files you've created so that they'll start running the next time the schedule dictates.
systemctl enable rsnapshot-daily.timer
systemctl enable rsnapshot-weekly.timer
systemctl enable rsnapshot-monthly.timer
The future
If this all seems more complex that it should be for scheduling rsnapshot backups, it is. Both rsnapshot
and your OS distribution could offer better support for systemd and sending-email-on-failure with systemd. If they did, you could get benefits using systemd timers with rsnapshot by using setting your MAILTO environment and running systemd enable
for the timers you wanted to turn on.
If this appeals to you, considering communicating with the rsnapshot
project and possibly submitting a pull request to improve support here.
Comments ()