Thursday, June 24, 2010

Script to backup directories on a regular basis

Update 28/06/2010 6:30:58 PM. This script works by copying directories. version 2 of this script backs up directories as ZIP files.

I have had many issues with backups. Let me re-phrase: I have had many issues with “Oh, what? I did WHAT? To all of them? How did that happen?” No more, I say! And this script is how I intend on making sure I has backups. I use it to make copies of each project directory I am actively working on right now.

The script below has two functions. The first is to backup a set of directories and delete old backups. You edit the script to define what directories it backs up, which directory they get backed up to and how long backups should be kept for. The second function is to schedule the script so that it will be called every few hours. You edit the script to define how often it should be called.

This is a Windows DOS Batch script. I have only tested it on Windows XP. It has one dependency, forfiles.exe which you can get from the magnificent site: An A-Z Index of the Windows XP command line. Make sure to put it in the path before running this script. Notes about running the script itself appear below the script.

@ECHO OFF

REM Directory backup utility.
REM - Written by Robert Mark Bram, 23/06/2010 5:10:55 PM.
REM - Tested on Win XP only.
REM - Dependency: forfiles.exe - get it from: http://ss64.com/nt/forfiles.html
REM    and make sure to put forfiles.exe in the PATH (e.g. C:\WINDOWS\system32\
REM    for Windows XP).

REM BACKUP AND DELETE OLD BACKUPS
REM Run this script without arguments and it will backup selected directories to
REM a backup directory and delete old backup directories.

REM SCHEDULE BACKUP TASKS
REM Run this script with argument "sched" and it will schedule this script to run
REM every few hours. You will need to enter your Windows password. For example:
REM    D:\work\MyProjects>backupDataHourly.bat sched
REM    Scheduling task.
REM    The task will be created under current logged-on user name ("SPIKE\Robert Bram").
REM    Please enter the run as password for SPIKE\Robert Bram: **************
REM
REM    SUCCESS: The scheduled task "Backup data hourly" has successfully been created.
REM    D:\work\MyProjects>
REM =======================================
REM EDIT THIS SECTION.
REM =======================================
REM Where do you want to put the backup files?
SET BACKUP_HOME=D:\files\backups

REM How long (days) do you want to keep them?
SET DAYS_B4_DELETE=10

REM Define path and label (no spaces) for each directory you want to backup.
SET DIR1="D:\work\MyProjects\FirstProject"
SET LBL1=FIRST_PROJ
SET DIR2="D:\work\MyProjects\SecondProject"
SET LBL2=SECOND_PROJ

REM How many dir/lbl combinations did you define?
SET MAX=2

REM How often (in hours) do you want to run this script?
SET HOURS=1

REM What name to give the scheduled task.
SET SCHED_TASK_LABEL=Backup data hourly



REM =======================================
REM DON'T CHANGE BELOW THIS POINT unless you know what you are doing!
REM =======================================

REM Directory Checks
IF "%BACKUP_HOME%" == "" (
   echo Warning: BACKUP_HOME has not been set.
   GOTO END
)
IF NOT EXIST "%BACKUP_HOME%"  (
   mkdir %BACKUP_HOME%
)
IF NOT EXIST "%BACKUP_HOME%"  (
   echo Warning: BACKUP_HOME [%BACKUP_HOME%] does not exist.
   GOTO END
)

REM Are we scheduling or backing up?
IF "%1" == "sched" GOTO :SCHEDULE
GOTO :BACKUP

REM Schedule this script to run regularly - user will have to enter password.
:SCHEDULE
echo Scheduling task.
schtasks /create /sc hourly /mo %HOURS% /tn "%SCHED_TASK_LABEL%" /tr %~dps0\%0
GOTO :END

REM Run backup tasks.
:BACKUP
echo Backing up files.

REM Create timestamp.
SET hh=%time:~0,2%
if "%time:~0,1%"==" " SET hh=0%hh:~1,1%
SET YYYYMMDD_HHMMSS=%date:~10,4%%date:~7,2%%date:~4,2%_%hh%%time:~3,2%%time:~6,2%

REM Backup selected paths.
SetLocal EnableDelayedExpansion
For /L %%i in (1,1,%MAX%) Do IF EXIST !DIR%%i! xcopy !DIR%%i! ^
   "%BACKUP_HOME%\!LBL%%i!_%YYYYMMDD_HHMMSS%" /D /E /C /I /H /R /Y
EndLocal

REM Delete old backups.
echo Deleting old files.
IF "%DAYS_B4_DELETE%" == "" (
   echo WARNING! DAYS_B4_DELETE not set. Not deleting old backups.
   GOTO :END
)

SetLocal EnableDelayedExpansion
For /L %%i in (1,1,%MAX%) Do (
   FORFILES -p"%BACKUP_HOME%" -m!LBL%%i!_* -d-%DAYS_B4_DELETE% ^
      -c"CMD /c rmdir /S /Q @FILE & echo @FILE will be deleted"
)
EndLocal

REM Use this for testing - echo what files will be deleted.
REM SetLocal EnableDelayedExpansion
REM For /L %%i in (1,1,%MAX%) Do (
REM    FORFILES -p"%BACKUP_HOME%" -m!LBL%%i!_* -d-%DAYS_B4_DELETE% ^
REM       -c"CMD /c echo @FILE will be deleted"
REM )
REM EndLocal

:END

REM Uncomment the "pause" line if you want the command window to stick around
REM until you "Press any key to continue . . ."
REM (Let's you see the output of every run.)
REM pause

You can run the script just by double clicking it or running it on the command line without any parameters, but the intention is that you schedule the script to run every few hours.

Save the script somewhere and edit the variables in the section labelled EDIT THIS SECTION. Make sure to give values to the variables there:

  • BACKUP_HOME - where to store the backups.
  • DAYS_B4_DELETE - how many days backups should be kept before deleting them.
  • DIRX and LBLX - a directory and label combination for each directory you want to back up. For example, DIR1="D:\work\MyProjects\FirstProject" and LBL1=FIRST_PROJECT will result in a backup directory being created such as FIRST_PROJECT_20100624_004014 - the label plus a time stamp.
  • MAX - how many DIRX and LBLX combinations you have (needed for loop control).
  • HOURS - how often to run the script (in hours).
  • SCHED_TASK_LABEL - what to call the task in the Scheduled Tasks applet.

Once you have edited the values, you can just run the script to create the backups - or you can run the script schedule backups by running it with the parameter “sched”. You will have to enter your login password. Here is an example:

D:\work\MyProjects>backupDataHourly.bat sched
Scheduling task.
The task will be created under current logged-on user name ("SPIKE\Robert Bram").
Please enter the run as password for SPIKE\Robert Bram: **************

SUCCESS: The scheduled task "Backup data hourly" has successfully been created.
D:\work\MyProjects>

So now I am sure I has backups!