Automation projects

Build a backup wrapper

Validate source and destination, create a dated archive, verify it, and report a clear result.

10 minute lesson

~~~

This module assembles the course pieces into small real tools, starting with a backup wrapper. The wrapper coordinates existing tools: validate the inputs, run tar, verify the result, report clearly. It should not pretend that creating an archive is a complete offsite backup.

The core operation

#!/usr/bin/env bash
set -euo pipefail

source_directory=${1:?source directory required}
destination=${2:?destination required}
archive="$destination/backup-$(date -u +%Y%m%dT%H%M%SZ).tar.gz"

tar -czf "$archive" -C "$source_directory" .
tar -tzf "$archive" >/dev/null
printf 'created %s\n' "$archive"

The ${1:?...} expansions reject missing arguments with a clear message and a non-zero status, so a half-configured run never starts. The timestamp from date -u +%Y%m%dT%H%M%SZ makes archive names sort chronologically, and two runs can’t silently overwrite each other.

tar -C "$source_directory" . changes into the source before archiving, so the archive stores relative paths. The second tar -tzf lists the finished archive and discards the listing: reading every entry back pushes the whole file through gzip, so a truncated or corrupt archive fails here — not on restore day.

./backup-wrapper /var/www/site /mnt/backups
# created /mnt/backups/backup-20260803T151530Z.tar.gz

Test the unhappy paths

Test with spaces in paths, insufficient permissions, a full destination, and a restore into a temporary directory:

./backup-wrapper '/var/www/my site' /mnt/backups   # spaces must survive
./backup-wrapper /root/private /mnt/backups        # tar must fail loudly, status non-zero
mkdir -p /tmp/restore-test
tar -xzf /mnt/backups/backup-20260803T151530Z.tar.gz -C /tmp/restore-test

The restore drill is the step people skip. An archive nobody has ever extracted is a hope, not a backup. Diff a few restored files against the originals before you trust the wrapper with anything real.

Know the wrapper’s limits

Do not archive a changing database and assume consistency. tar reads files one at a time, so a database writing during the walk produces an archive whose files never coexisted — it may not restore at all. Use the database’s backup mechanism, like pg_dump or mysqldump, and archive its output instead.

And a .tar.gz sitting on the same machine protects against mistakes, not disk failure. Copying archives somewhere independent is the missing half of the job.

Lesson completed

Take this course offline

Get every free book and course as PDF and EPUB files.

Get the download library →