Tim's Blog

Information, Technology, Security, and other stuff.

Simple CentOS 7 Backups with Duplicity

Published 2016-06-10

I wrote a little while ago about creating compressed, encrypted backups of both Windows and Linux machines.

For Linux, there isn't a "bare metal" style backup that can be performed because, well, there's no point. Everything is a file on Linux, so just make a copy of every file to perform the backup. Restore the files over the top of an existing installation to recover.

So to do this I had a script run that tar's the whole root filesystem, and then encrypts it with OpenSSL. I later found I could kill two birds with one command and just use 7zip to compress and encrypt at the same time.

Then, digging around some more later, I found that Duplicity basically does all of this, is a lot simpler to use and also does incremental backups.

The documentation, as with most FOSS projects, can be a little confusing, so here's what I did to set up backups of all my servers to a single backup host. I've said CentOS 7 in the title, but this will really apply to any popular distro, aside from the duplicity installation step.

Setting up the Backup Host

I made a minimal CentOS 7 VM to act as the backup destination on my network. I installed nothing on it. I then created a second 1TB Virtual Disk, and mounted it in the machine.

mkdir /mnt/backups
mount /dev/sdb1 /mnt/backups

Then I created a user (non-admin) that the client machines can log into the server as to store their backups. I also set up SSH keys for the client machines to authenticate with, as I disable password logon over SSH on every machine I build.

# Add the user (the name isn't important)
useradd duplicity

# Set up the backup destination
chmod 700 /mnt/backups/
chown duplicity:duplicity /mnt/backups/

# Switch over to the backup user
su - duplicity
mkdir .ssh
touch .ssh/authorized_keys
chmod 755 .ssh/
chmod 644 .ssh/authorized_keys

Setting up the Backup Clients

Now over to the backup clients. I run the backups using cron under the root account, so I had to create an SSH key for the root account to use to authenticate to the Backup Server. I also disable root access over SSH, so using the root account on the Backup Server was out of the question.

I ran the following:

# Switch over to the Root Account
sudo su

# Install Duplicity
yum install epel-release -y && yum install duplicity -y

# Create the SSH Key for the root account
cd ~
mkdir .ssh
chmod 755 .ssh/
ssh-keygen -t rsa

touch .ssh/known_hosts

I copied the contents of /etc/ssh/ssh_host_rsa_key.pub on the Backup Server into .ssh/known_hosts, otherwise duplicity wouldn't run because it didn't trust the server.

Then I got a copy of the public key:

cat .ssh/id_rsa.pub

And pasted that into the /home/duplicity/.ssh/authorized_keys file on the Backup Server. You can add as many different keys as you wish, and I recommend generating a keypair on every server that you connect to the Backup Server.

Scheduling the Backups

Then it was as simple as adding an entry to the /etc/crontab file to schedule the backups. This example runs every day at 01:00, and backs up / and excludes /proc, /sys, /tmp and /mnt. I put $HOSTNAME at the end of the path so it'll create a directory for each server based on their hostnames.

0 1 * * * root PASSPHRASE="MaKeThIsAgOoDpAsSwOrD" duplicity --exclude /sys --exclude /proc --exclude /tmp --exclude /mnt / scp://duplicity@BACKUPSERVERHOSTNAME:22//mnt/backups/$HOSTNAME

Make sure that your backups go into individual directories, or you'll experience odd behaviour. I also recommend you stagger multiple backup jobs with at least 30 mins time between them, so you're not thrashing the drive with simultaneous writes from every backup happening at once.

Duplicity will automagically create a full backup the first time it runs, and then create incremental backups every day after that.

Also the PASSPHRASE parameter will encrypt the backups. If you don't specify it, it'll prompt for a password (unless you add the switch to bypass encryption).