Incrimental Backups: Difference between revisions

From James's Wiki
No edit summary
No edit summary
 
(2 intermediate revisions by the same user not shown)
Line 1: Line 1:
Here is a bash script to do incrimental backups via ssh and rsync.
Here is a bash script to do incrimental backups via ssh and rsync.


<syntaxhighlight lang="Bash">
  #!/bin/bash
  #!/bin/bash
#do the usage or help section
  #default port if none given
  #default port if none given
   
   
Line 494: Line 494:
         fi
         fi
  fi
  fi
</syntaxhighlight>

Latest revision as of 20:36, 29 April 2019

Here is a bash script to do incrimental backups via ssh and rsync.

 #!/bin/bash
 #default port if none given
 
 getopt --test > /dev/null
 if [[ $? -ne 4 ]]; then
    echo "I’m sorry, `getopt --test` failed in this environment."
    exit 1
 fi
 
 OPTIONS=hdwmtvp:rl:
 LONGOPTIONS=hourly,daily,weekly,monthly,test,verbose,port:,rsyncskip,login:

 # -temporarily store output to be able to check for errors
 # -e.g. use “--options” parameter by name to activate quoting/enhanced mode
 # -pass arguments only via   -- "$@"   to separate them correctly
 PARSED=$(getopt --options=$OPTIONS --longoptions=$LONGOPTIONS --name "$0" -- "$@")
 if [[ $? -ne 0 ]]; then
    # e.g. $? == 1
    #  then getopt has complained about wrong arguments to stdout
    echo "This is an incrimental backup system designed to make backups from remote systems to the local system"
    echo "You can also make backups from the local system to the local system"
    echo "This script is designed to be run as a cronjob and normally will provide no output"
    echo "Since this script is run as a  cronjob and uses ssh to connect to remote servers, you must use ssh-keys to avoid password prompts"
    echo
    echo "USAGE: ./testscript [options] <source> <destination>"
    echo "The options are:"
    echo "-h or --hourly for preforming hourly incrimental backups"
    echo "-d or --daily for preforming daily incrimental backups"
    echo "-w or --weekly for preforming weekly incrimental backups"
    echo "-m or --monthly for preforming monthly incrimental backups"
    echo "-t or --test for test mode. The program will run through the process of prefroming a backup without actually makeing any real changes"
    echo "-v or --verbose adds output for testing purposes"
    echo "-l or --login <someuser@1.2.3.4> used to specify your username and the ip address of the remote server"
    echo "-p or --port <1234> used to specify the remote servers port to connect to. The default is 22"
    echo "-r or rsyncskip used to skip the rsync dry-run command if your trying to see whats going on with -v or --verbose and rsync is filling up your scroll buffer"
    exit 2
 fi
 # read getopt’s output this way to handle the quoting right:
 eval set -- "$PARSED"
 
 # now enjoy the options in order and nicely split until we see --
 while true; do
    case "$1" in
        -h|--hourly)
		MODE=HOURLY
         	shift
	        ;;
        -d|--daily)
		MODE=DAILY
	        shift
        	;;
	-w|--weekly)
		MODE=WEEKLY
		shift
		;;
	-m|--monthly)
		MODE=MONTHLY
		shift
		;;
	-t|--test)
		TESTRUN=YES
		shift
		;;
        -v|--verbose)
		VERBOSE=YES
		shift
		;;
	-p|--port)
		PORT="-p $2";
		shift 2;;
  -l|--login)
    LOGIN="$2";
    shift 2;;
	-r|--rsyncskip)
		RSYNCSKIP=YES
		shift;;
  -H|--help)
    echo "This is an incrimental backup system designed to make backups from remote systems to the local system"
    echo "You can also make backups from the local system to the local system"
    echo "This script is designed to be run as a cronjob and normally will provide no output"
    echo "Since this script is run as a  cronjob and uses ssh to connect to remote servers, you must use ssh-keys to avoid password prompts"
    echo
    echo "USAGE: ./testscript [options] <source> <destination>"
    echo "The options are:"
    echo "-h or --hourly for preforming hourly incrimental backups"
    echo "-d or --daily for preforming daily incrimental backups"
    echo "-w or --weekly for preforming weekly incrimental backups"
    echo "-m or --monthly for preforming monthly incrimental backups"
    echo "-t or --test for test mode. The program will run through the process of prefroming a backup without actually makeing any real changes"
    echo "-v or --verbose adds output for testing purposes"
    echo "-l or --login <someuser@1.2.3.4> used to specify your username and the ip address of the remote server"
    echo "-p or --port <1234> used to specify the remote servers port to connect to. The default is 22"
    echo "-r or rsyncskip used to skip the rsync dry-run command if your trying to see whats going on with -v or --verbose and rsync is filling up your scroll buffer"
    echo
    exit 0;
		;;
        --)
		shift
		break
		;;
        *)
		echo "Programming error"
            	exit 3
            	;;
    esac
 done

 # handle non-option arguments
 if [[ $# -ne 2 ]]; then
    echo "$0: A single input file is required."
    exit 4
 fi
 
 # test to make sure the source exists and is reachable
 if [ -n "$LOGIN" ]; then
  if ! ssh "$PORT" "$LOGIN" ls "$1" >/dev/null 2>&1  ; then
	   echo "ERROR Target Directory: $2 is unreachable or does not exist"
	   exit 1;
  else
	     SOURCE="$LOGIN:$1"
  fi
 else
  SOURCE="$1"
 fi
 
 #check to see if the destination dir exists
 if [ -d "$2" ]; then
  TRG="$2"
 else
  echo "destination directory doesn't exist."
  exit 1;
 fi
 
 # Perform an hourly backup
 if [ $MODE = HOURLY ]; then
	#Today's date:
	DAY0=`date +%Y_%a_%b_%d_%H`
	#Today's date minus 25 hours
	DAY24=`date -d "25 hours ago" +%Y_%a_%b_%d_%H`
	#One hour ago:
	DAY1=`date -d "1 hour ago" +%Y_%a_%b_%d_%H`

	#The target directory:
	TRG+=$DAY0

  #The Link Dir
        LNKDIR="/media/4USB/backup/sserver/$DAY1/"

	if [ -d "$LNKDIR" ]; then
		LNK="--link-dest=$LNKDIR"
	else
		LNK=""
	fi

        #Set rsync run options
        if [[ $TESTRUN = YES ]]; then
                if [[ $VERBOSE = YES ]]; then
                        #Verbose + Test Mode
                        OPT="-ahvn --delete"
                        echo "Hourly Mode: Verbose + Test Mode"
                        echo
                else
                        #Quite + Test Mode
                        OPT="-ahqn --delete"
                fi
        else
                if [[ $VERBOSE = YES ]]; then
                        #Verbose + Real Run
                        OPT="-ahv --delete"
                        echo "Hourly Mode: Verbose + Real Run"
                        echo
                else
                        #Quiet + Real Run
                        OPT="-ahq --delete"
                fi
        fi

	if [[ $VERBOSE = YES ]]; then
                echo "This script will backup files from:"
                echo "$SOURCE"
                echo
                echo "To:"
                echo "$TRG"
                echo
                if [ -d "$LNKDIR" ]; then
                        echo "The files in: $SOURCE that match the files in"
                        echo "$LNKDIR will be symbolicly linked instead of copied"
                else
                        echo "This must be the first time a backup of this type has"
                        echo "been made because the link directory: $LNKDIR does not exist"
                fi
                echo
                echo "The rsync command that will be used is:"
                echo "rsync "$OPT $LNK -e "'ssh -p 2222'" $SRC $TRG
                echo
	fi
 
	#Execute the backup
	if [[ $RSYNCSKIP != "YES" ]]; then
		rsync $OPT $LNK -e 'ssh -p 2222' $SOURCE $TRG
	fi
 
        #Delete the backup from 25 hours ago, if it exists
        if [[ $VERBOSE = YES ]]; then
                if [ -d /media/4USB/backup/sserver/$DAY24 ]; then
                        echo "Old backup found."
                        echo
                        if [[ $TESTRUN = YES ]]; then
                                echo "simulatingdeleting old backup:"
                                echo "rm -Rf /media/4USB/backup/sserver/$DAY24"
                        fi
                else
                        echo "Old backup from 25 hours ago NOT found"
                        echo
                fi
        else
                if [ -d /media/4USB/backup/sserver/$DAY24 ]; then
                        if [[ $TESTRUN != YES ]]; then
                                rm -Rf /media/4USB/backup/sserver/$DAY24
                        fi
                fi
        fi
 
 elif [ $MODE = DAILY ]; then
  #Today's date:
  DATE_TODAY=`date +%Y_%a_%b_%d`
	#The date at last midnight******maybe check and see if it exists if not then error out*****
	DATE_LAST_MIDNIGHT=`date -d "1 day ago" +%Y_%a_%b_%d_00`
	#DATE_8_DAYS_AGO
	DATE_8_DAYS_AGO=`date -d "8 days ago" +%Y_%a_%b_%d`

        #The target directory:
        TRG+=$DAY0

        #The Link Dir
        LNKDIR="/media/4USB/backup/sserver/$DATE_LAST_MIDNIGHT/"

        if [ -d "$LNKDIR" ]; then
                LNK="--link-dest=$LNKDIR"
        else
                LNK=""
        fi

        #Set rsync run options
        if [[ $TESTRUN = YES ]]; then
		if [[ $VERBOSE = YES ]]; then
			#Verbose + Test Mode
			OPT="-ahvn --delete"
			echo "Daily Mode: Verbose + Test Mode"
			echo
		else
			#Quite + Test Mode
			OPT="-ahqn --delete"
		fi
        else
		if [[ $VERBOSE = YES ]]; then
			#Verbose + Real Run
			OPT="-ahv --delete"
			echo "Daily Mode: Verbose + Real Run"
			echo
		else
			#Quiet + Real Run
			OPT="-ahq --delete"
		fi
        fi
 
        if [[ $VERBOSE = YES ]]; then
                echo "This script will backup files from:"
                echo "$SOURCE"
                echo
                echo "To:"
                echo "$TRG"
                echo
                if [ -d "$LNKDIR" ]; then
                        echo "The files in: $SOURCE that match the files in"
                        echo "$LNKDIR will be symbolicly linked instead of copied"
                else
                        echo "This must be the first time a backup of this type has"
                        echo "been made because the link directory: $LNKDIR does not exist"
                fi
                echo
                echo "The rsync command that will be used is:"
                echo "rsync "$OPT $LNK -e "'ssh -p 2222'" $SRC $TRG
                echo
        fi
 
	#Execute the backup
        if [[ $RSYNCSKIP != "YES" ]]; then
                rsync $OPT $LNK -e 'ssh -p 2222' $SOURCE $TRG
        fi
 
        #Delete the backup from 8 days ago, if it exists
        if [[ $VERBOSE = YES ]]; then
                if [ -d /media/4USB/backup/sserver/$DATE_8_DAYS_AGO ]; then
                        echo "Old backup found."
                        echo
                        if [[ $TESTRUN = YES ]]; then
                                echo "simulatingdeleting old backup:"
                                echo "rm -Rf /media/4USB/backup/sserver/$DATE_8_DAYS_AGO"
                        fi
                else
                        echo "Old backup from 8 days ago NOT found"
                        echo
                fi
        else
                if [ -d /media/4USB/backup/sserver/$DATE_8_DAYS_AGO ]; then
                        if [[ $TESTRUN != YES ]]; then
                                rm -Rf /media/4USB/backup/sserver/$DATE_8_DAYS_AGO
                        fi
                fi
        fi
 
 #Weekly backup. Saves 4 weeks worth of backups.
 elif [ $MODE = WEEKLY ]; then
        #Today's week number:
        DATE_THIS_WEEK=`date +%Y_Week_%U`
	#Today's date:
        DATE_TODAY=`date +%Y_%a_%b_%d`
	#Date one week ago
	DATE_5_WEEKS_AGO=`date -d "5 weeks ago" +%Y_Week_%U`
 
        #The target directory:
        TRG+=$DAY0
        #The Link Dir
        LNKDIR="/media/4USB/backup/sserver/$DATE_5_WEEKS_AGO/"
 
        #Check and see if the link directory exists. if not then don't use the rsync --link-dest option
        if [ -d "$LNKDIR" ]; then
                LNK="--link-dest=$LNKDIR"
        else
                LNK=""
        fi
 
        #Set rsync run options
        if [[ $TESTRUN = YES ]]; then
                if [[ $VERBOSE = YES ]]; then
                        #Verbose + Test Mode
                        OPT="-ahvn --delete"
                        echo "Weekly Mode: Verbose + Test Mode"
                        echo
                else
                        #Quite + Test Mode
                        OPT="-ahqn --delete"
                fi
        else
                if [[ $VERBOSE = YES ]]; then
                        #Verbose + Real Run
                        OPT="-ahv --delete"
                        echo "Weekly Mode: Verbose + Real Run"
                        echo
                else
                        #Quiet + Real Run
                        OPT="-ahq --delete"
                fi
        fi

        if [[ $VERBOSE = YES ]]; then
                echo "This script will backup files from:"
		echo "$SOURCE"
		echo
		echo "To:"
		echo "$TRG"
		echo
		if [ -d "$LNKDIR" ]; then
	                echo "The files in: $SOURCE that match the files in"
			echo "$LNKDIR will be symbolicly linked instead of copied"
	        else
	                echo "This must be the first time a backup of this type has"
			echo "been made because the link directory: $LNKDIR does not exist"
	        fi
		echo
                echo "The rsync command that will be used is:"
                echo "rsync "$OPT $LNK -e "'ssh -p 2222'" $SRC $TRG
		echo
        fi

        #Execute the backup
        if [[ $RSYNCSKIP != "YES" ]]; then
                rsync $OPT $LNK -e 'ssh -p 2222' $SOURCE $TRG
        fi

	#Delete the backup from 5 weeks ago, if it exists
	if [[ $VERBOSE = YES ]]; then
		if [ -d /media/4USB/backup/sserver/$DATE_5_WEEKS_AGO ]; then
			echo "Old backup found."
			echo
			if [[ $TESTRUN = YES ]]; then
	                        echo "simulatingdeleting old backup:"
				echo "rm -Rf /media/4USB/backup/sserver/$DATE_5_WEEKS_AGO"
			fi
		else
			echo "The Old backup from 5 weeks ago was NOT found"
			echo
		fi
	else
                if [ -d /media/4USB/backup/sserver/$DATE_5_WEEKS_AGO ]; then
                        if [[ $TESTRUN != YES ]]; then
				rm -Rf /media/4USB/backup/sserver/$DATE_5_WEEKS_AGO
			fi
                fi
	fi

 #Monthly backup. Saves 12 months worth of backups.
 elif [ $MODE = MONTHLY ]; then
        #Today's week number:
        DATE_THIS_MONTH=`date +%Y_%m`
        #Today's date:
        DATE_TODAY=`date +%Y_%a_%b_%d`
        #Date one week ago
        DATE_13_MONTHS_AGO=`date -d "13 months ago" +%Y_%m`

        #The target directory:
        TRG+=$DAY0
        #The Link Dir
        LNKDIR="/media/4USB/backup/sserver/$DATE_13_MONTHS_AGO/"

        #Check and see if the link directory exists. if not then don't use the rsync --link-dest option
        if [ -d "$LNKDIR" ]; then
                LNK="--link-dest=$LNKDIR"
        else
                LNK=""
        fi

        #Set rsync run options
        if [[ $TESTRUN = YES ]]; then
                if [[ $VERBOSE = YES ]]; then
                        #Verbose + Test Mode
                        OPT="-ahvn --delete"
                        echo "Monthly Mode: Verbose + Test Mode"
                        echo
                else
                        #Quite + Test Mode
                        OPT="-ahqn --delete"
                fi
        else
                if [[ $VERBOSE = YES ]]; then
                        #Verbose + Real Run
                        OPT="-ahv --delete"
                        echo "Monthly Mode: Verbose + Real Run"
                        echo
                else
                        #Quiet + Real Run
                        OPT="-ahq --delete"
                fi
        fi

        if [[ $VERBOSE = YES ]]; then
                echo "This script will backup files from:"
                echo "$SOURCE"
                echo
                echo "To:"
                echo "$TRG"
                echo
                if [ -d "$LNKDIR" ]; then
                        echo "The files in: $SOURCE that match the files in"
                        echo "$LNKDIR will be symbolicly linked instead of copied"
                else
                        echo "This must be the first time a backup of this type has"
                        echo "been made because the link directory: $LNKDIR does not exist"
                fi
                echo
                echo "The rsync command that will be used is:"
                echo "rsync "$OPT $LNK -e "'ssh -p 2222'" $SRC $TRG
                echo
        fi

        #Execute the backup
        if [[ $RSYNCSKIP != "YES" ]]; then
                rsync $OPT $LNK -e 'ssh -p 2222' $SOURCE $TRG
        fi

        #Delete the backup from 13 months ago, if it exists
        if [[ $VERBOSE = YES ]]; then
                if [ -d /media/4USB/backup/sserver/$DATE_13_MONTHS_AGO ]; then
                        echo "Old backup found."
                        echo
                        if [[ $TESTRUN = YES ]]; then
                                echo "simulatingdeleting old backup:"
                                echo "rm -Rf /media/4USB/backup/sserver/$DATE_5_WEEKS_AGO"
                        fi
                else
                        echo "The Old backup from 13 months ago was NOT found"
                        echo
                fi
        else
                if [ -d /media/4USB/backup/sserver/$DATE_13_MONTHS_AGO ]; then
                        if [[ $TESTRUN != YES ]]; then
                                rm -Rf /media/4USB/backup/sserver/$DATE_13_MONTHS_AGO
                        fi
                fi
        fi
 fi