I’m hosting a website for a friend and the other day he inquired if I was backing up the data on his website since he was going to update his site and wanted to make sure he could recover the site in case everything went fubar.  I hadn’t really put much thought into regular backups, I guess it was always something “I was going to get around to” but never had the time or need since I do take regular backups of the databases and most of my important stuff reside in them.   So in accordance to the old saying ; you can never have too many backups, I saw this as an oppurtunity to get some excercise in shell scripting by putting together a basic script to make a weekly snapshot of my sites and daily incremental backups.  This is just a very simple script that creates local backups using tar of everything in a folder. except the log files. Then I have another script that will copy the backups to an off-site location.

# Author:
#  Johannes Helgi Laxdal
#   http://www.laxdal.org
#    2012
# Simple script to manage weekly snapshot backups and daily incremental backups of multiple websites.
# This script assumes your web folder structure is something like this :
#   /path/to/www/site1/   (Directory containing everything that belongs to the website, script supports multiple sites, i.e. site1, site2, site3, etc)
#   /path/to/www/site1/public_html   (or whatever the document_root is called)
#   /path/to/www/site1/logs   (where you keep logs)
#   /path/to/www/site1/folder1   ([optional] any number of other directories or files)
#  The script backs up everything inside /path/to/www/site1/ except the logs directory, if you need or want
# to backup the logs directory then just edit the tar command and take out the --exclude statement.
#  The backup destination structure is like this
#    /path/to/backup/site1/   (directory containing every backup and incremental backup of the given site)
#    /path/to/backup/site1/weekXX   (every backup session is 1 week long and goes in its own directory where XX is the number week number)
#    /path/to/backup/site1/weekXX/backup.log   (the incremental backup log for Tar)
#    /path/to/backup/site1/weekXX/site1.backupY.tar.gz   (the backup file itself where Y is the day of the week. First backup file (lowest Y) is the snapshot and the rest are increments)
#    /path/to/backup/site1/weekXX/results.log   (the output from the tar executions)

#Get our Time Variables
WEEK="$(date +"%V")"
DOW="$(date +"%u")"
DATE="$(date +"%d/%m/%y")"

# Begin our benchmark
START=$(($(date +%s%N)/1000000))

# What do we want to backup (/path/to/www/ in the description)

# Where do we store all our backups (/path/to/backup/ in the description)

# Then we need to make sure the directory we need to backup does indeed exist
if [ ! -d "$SOURCE_ROOT" ]; then
  echo "Backup source does not exist."
  exit 1 # Backup target doesn't exist

# First let's make sure the directory where we store our backups exists.
if [ ! -d "$DESTINATION_ROOT" ]; then
  echo "Backup destination does not exist."
  exit 1 # Backup store doesn't exist.

# Beginning Daily Backup Process
echo "Beginning Daily Backup : $DATE "

# Get a list of all the sites we want to backup

# Go through all of our sites
for SITE in $SITES
 # Announce our current target
 echo "Processing $SITE"

 # Speed test start
 SITESTART=$(($(date +%s%N)/1000000))

 # Does our site backup directory exist?
  if [ ! -d "$DESTINATION_ROOT/$SITE" ]; then
    echo "Site Backup Directory doesn't exist, we need to create it"

 # Does our weekly backup directory exist?
 if [ ! -d "$DESTINATION_ROOT/$SITE/week$WEEK" ]; then
  echo "Weekly Backup Directory doesn't exist, we need to create it"

 # We should now be ready to begin backing up. We skip the Logs, we (I) don't need to back them up.
 tar -g "$DESTINATION_ROOT/$SITE/week$WEEK/backup.log" -zcvpf "$DESTINATION_ROOT/$SITE/week$WEEK/$SITE.backup$DOW.tar.gz" --exclude="$SITE/logs/*" --exclude="$SITE/logs" -C $SOURCE_ROOT $SITE >> $DESTINATION_ROOT/$SITE/week$WEEK/results.log 2>&1 || echo "There was an error executing tar"

 # Calculate how long we took
 SITEEND=$(($(date +%s%N)/1000000))

 # We should now be done
 echo "Done processing $SITE in $SITETAKEN ms"

# Get the Unixtimestamp of when we end
END=$(($(date +%s%N)/1000000))

# We're done
echo "Done backing up in $TAKEN ms"

Just put this into the cron.daily or crontab and it should take care of itself.

Tagged with: