Guy Rutenberg

Keeping track of what I do

Improved FTP Backup for WordPress

with 13 comments

This script backups both the database and files of a WordPress blog into a remote FTP server (while keeping a local copy). It’s an update of my WordPress Backup to FTP script. The main changes are auto-detecting database settings and better support for caching plugins (specifically WP-Cache). The new version makes it easier to backup multiple WordPress blogs to the same FTP server.

Usage is pretty simple after a short initial configuration. First, save the the script and make it executable:

chmod +x wp-backup

(assuming you saved it under the name wp-backup). After saving it edit the file with your favorite editor and set the 5 configuration variable to whatever is appropriate for you. BACKUP_DIR is the folder to save the local backups to. FTP_HOST, FTP_USER, FTP_PASS control the FTP host, username and password, respectively, for the remote backup server. FTP_BACKUP_DIR sets the folder on the FTP server to save the remote backup to.

Now that the initial configuration is done, all you need to do is execute the script and give the path to the blog as an argument. For example:

./wp-backup /home/someuser/myblog

And that it, the script will backup your files (excluding cache) and database to both a local and remote locations. This allows using the same script to backup multiple WordPress blogs, unlike the previous script which had to be modified for each blog.

And now the script itself:

#!/bin/bash
 
# Copyright 2008, 2010 Guy Rutenberg <http://www.guyrutenberg.com/contact-me>
# WordPress FTP backup 2.0
#
# Easily backup wordpress instances via ftp.
#
# Change Log:
# ===========
# 2.0:
#  - Auto-detect database settings.
#  - Exclude cache data from backups.
 
BACKUP_DIR=
FTP_HOST=
FTP_USER=
FTP_PASS=
FTP_BACKUP_DIR=
 
# end of configuration - you probably don't need to touch anything bellow
 
PROG=`basename "$0"`
print_usage () {
    echo "USAGE: ${PROG} [options] BLOG_ROOT"
    echo "Backup a WordPress blog"
}
 
print_help ()  {
    print_usage
    cat << EOF
 
Options:
    -h, --help          show this help message and exit
 
EOF
}
 
TEMP=`getopt -o h --long help -n "$PROG" -- "$@"`
if (($?)); then
    print_usage
    exit 1
fi
 
eval set -- "$TEMP"
 
while true ; do
    case "$1" in
        -h|--help) print_help; exit ;;
        --) shift; break;;
    esac
done
 
if [ -z "$1" ]
then
 print_usage > /dev/stderr
 exit 1
fi
 
BLOG_DIR=$1
DB_NAME=`echo "<?php require_once(\"${BLOG_DIR}/wp-config.php\"); echo DB_NAME;" | php`
DB_USER=`echo "<?php require_once(\"${BLOG_DIR}/wp-config.php\"); echo DB_USER;" | php`
DB_PASS=`echo "<?php require_once(\"${BLOG_DIR}/wp-config.php\"); echo DB_PASSWORD;" | php`
DB_HOST=`echo "<?php require_once(\"${BLOG_DIR}/wp-config.php\"); echo DB_HOST;" | php`
 
BLOG_DIR=`dirname "$BLOG_DIR"`/`basename "$BLOG_DIR"`
BACKUP_DIR=`dirname "$BACKUP_DIR"`/`basename "$BACKUP_DIR"`
 
echo -n "dumping database... "
DUMP_NAME=${DB_NAME}-$(date +%Y%m%d).sql.bz2
mysqldump --user=${DB_USER} --password=${DB_PASS} --host=${DB_HOST} \
 --databases ${DB_NAME} \
 | bzip2 -c > ${BACKUP_DIR}/${DUMP_NAME}
if [ "$?" -ne "0" ]; then
	echo "failed!"
	exit 1
fi
echo "done"
 
echo -n "Creating tarball... "
TAR_NAME=${BLOG_DIR##*/}-$(date +%Y%m%d).tar.bz2
tar -cjf ${BACKUP_DIR}/${BLOG_DIR##*/}-$(date +%Y%m%d).tar.bz2 --exclude cache ${BLOG_DIR}
if [ "$?" -ne "0" ]; then
	echo "failed!"
	exit 2
fi
echo "done"
 
echo -n "Uploading SQL dump and tarball to FTP... "
lftp -u ${FTP_USER},${FTP_PASS} ${FTP_HOST} <<EOF
cd "${FTP_BACKUP_DIR}"
put "${BACKUP_DIR}/${DUMP_NAME}"
put "${BACKUP_DIR}/${TAR_NAME}"
 
EOF
if [ "$?" -ne "0" ]; then
	echo "failed!"
	exit 3
fi
echo "done"
Share and Enjoy:
  • del.icio.us
  • StumbleUpon
  • Digg
  • Facebook
  • Mixx
  • Google Bookmarks
  • Simpy

Written by Guy

February 28th, 2010 at 8:38 am

Posted in Bash, Projects, Wordpress

Tagged with , ,

13 Responses to 'Improved FTP Backup for WordPress'

Subscribe to comments with RSS or TrackBack to 'Improved FTP Backup for WordPress'.

  1. Thank you, this is an awesome script! Unfortunatley, it only allows one backup a day… how would one modify it to allow hourly backups?

    I assume it would be by modifying (date +%Y%m%d) to include the time?

    Steve

    9 Mar 10 at 11:45

  2. yes, be sure to update all occurrences or else you might encounter some strange behavior.

    Guy

    9 Mar 10 at 21:04

  3. Thanks for the great script, not sure if this is an issue with my host [GoDaddy] but I seem to get the following response:

    Set-Cookie: bb2_screener_=1268525451+; path=/
    Content-type: text/html

    when the script tries to run the DB_NAME / DB_USER assignments through the portion of the script. Not sure what I am doing wrong, and running the echo command straight from shell produces same result.

    A workaround I guess would be to manually specify the DB info [as in your old version of script] but this defeats the point of a nice “automatic” detection for multiple-WP installs.

    Thanks!

    Alex

    14 Mar 10 at 02:15

  4. Do you have a fully functional shell on your GoDaddy server? Past experience teach taught me that GoDaddy doesn’t provide a full shell access, which makes running many scripts impossible (and probably this one too).

    Guy

    14 Mar 10 at 07:35

  5. actually after some long trial and error it would seem that the following part of script (for all 4 variables)

    DB_HOST=`echo “<?php include(\"${BLOG_DIR}/wp-config.php\"); echo DB_HOST;" | php`

    the php include part was returning some kind of header information in addition to the DB_HOST variable and therefore once I stripped that out by adding the following lines underneath it seemed to work.

    DB_HOST=`echo "<?php include(\"${BLOG_DIR}/wp-config.php\"); echo DB_HOST;" | php`
    DB_HOST=`echo $DB_HOST | tr -d '\r\n'`
    DB_HOST=${DB_HOST##* }

    Now on to find lftp alternative that works with GoDaddy *sigh*

    Alex

    14 Mar 10 at 07:52

  6. [...] скрипт лежит тут. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 [...]

  7. I created an .exe file with the sript you provide and when trying to run it I got this message:

    “The version of this file is not compatible with the version of Windows you’re running. Check your computer’s system information to see whether you need an x86 (32-bit) or x64 (64-bit) version of the program and then contact the software publisher”.

    My OS is Windows 7 – x64

    Any insight and am I doing everything right?

    Thanks.

    Rafael M

    9 Apr 10 at 19:03

  8. This is a bash script, how did you turn it into an exe?
    Anyway, you’ll need bash in order to run it (which probably means you’ll need some sort of Linux or BSD).

    Guy

    10 Apr 10 at 12:54

  9. This allows using the same script to backup multiple WordPress blogs, unlike the previous script which had to be modified for each blog.

    Does this mean there’s support for WPMU and Multiple DBs?

    If so, is there any other setup info we need to do to make it work?

    Nick

    2 Jun 10 at 17:47

  10. I meant that the script can be used to backup multiple regular WP blogs. I’m not familiar enough with WPMU to be sure, but I think it might work. Just try it. I don’t think it will work with multiple dbs serving one installation.

    Guy

    4 Jun 10 at 14:46

  11. Hello Guy,

    Can you give me so direction on how to solve this error?

    dumping database… ./wp-backup: line 72: ${BACKUP_DIR}/${DUMP_NAME}: ambiguous redirect
    mysqldump: unknown option ‘-2′
    failed!

    Your previous WP FTP script is working quite well on the same server.

    Thank you.

    Ed

    17 Jun 10 at 04:50

  12. Mit dem Auto nach Guadalest…

    weil auch hier und hier über Autourlaub berich…

    Kurortmeinung.de

    8 Jul 10 at 18:41

  13. Hi Guy

    Same error
    dumping database… ./wp-backup: line 72: ${BACKUP_DIR}/${DUMP_NAME}: ambiguous redirect
    mysqldump: unknown option ‘-2′
    failed!

    Manually ran the script for the echo DB_NAME bit and it may be wordpress v3.0 call wp-settings.php then it call something else and never actually ECHO DB_NAME.

    Hope this is making sense.

    Cheers
    Eric

    Eric Tam

    30 Jul 10 at 12:05

Leave a Reply