I recently started using the VMWares Consolidated Backup product to backup the virtual servers on our VMWare ESX hosts. Dues to our VCB proxy server only having a 40Gb Hard Drive we where having problems with the pre-command script that comes with the Backup Exec integration module for VCB.
The normal way VCB and Backup exec works is you would create a single backup job and add all of your virtual servers to the pre-command and to the selection list of the Backup Exec job, The problem with that is your VCB proxy server needs to have enough disk space to temporarily store the snapshots of all of your virtual servers you are backing up, for us and our 25 virtual servers this was around 300Gb.
We could have given our VCB proxy server some of our San space but that seemed a waste of 300Gb, we could of put a couple of large SCSI disk in the VCB proxy to act as a staging area but our VCB server had no more room for any more disks, we could of also created a separate backup exec job for each virtual server but that just gets messy with the scheduling of the jobs.
The solution I whent for was to create a vbs script that runs though a list of servers in a text file and for each server it creates a temporary backup job in real times with the correct pre / post commands and selection list, waits for that servers job to finish and then moves on to the next server in the text file.
This makes adding a new server to be backed up very easy as you just add the server name to the bottom of a text file, it also means you staging disk only needs to be bigger that the largest amount of used space on your largest virtual server. For us that is about 30Gb.
Before you begin you should do some reading about VCB, you should download and install the backup exec integration module. If there is enough domand I will write a full tutorial?
Here is my vbs script, be warned I give no support and hold no responsibility for any problems you may have or if you kill your servers etc. But please feel free to post any comments or questions.
te a text file with the list of your server name in C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\vcb_servers_list.txt. With a server name on each line for example;
Server1
Server2
Server4
Server3
The script assumes the default installation directories for VCB and Backup Exec
You will need to create a template backup exec script file under C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\vcb_backup_job_template.txt
The script only works for taking full backups of servers, I am working on something more advanced.
You will need to change the “domainname.co.uk” part of “.domainname.co.uk-FullVM” to your domain name.
Here is how my Backup Exec Script template looks, take a look at the bemcmd command line reference on the backup exec website for more options;
'---------------------------- 'Define '---------------------------- set WshShell=WScript.CreateObject ("WScript.Shell") Set wshFSO=Createobject("Scripting.FileSystemObject") Const ForReading = 1 Const ForWriting = 2 Const ForAppending = 8 sJobName = "Vmware_VCB" sServerList = "" sFileLoc = "C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\vcb_servers_list.txt" sBackupScript = "C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\vcb_backup_job.txt" sFileLogPath = "C:\Logs\" ' BUILD FILENAME tmpDate = date tmpTime = time sDate = Replace(tmpDate, "/", "-") sTime = Replace(tmpTime, ":", "-") 'sFileLogName = sDate & " " & sTime & ".log" sFileLogName = sDate & "_" & sTime & ".log" Set objLogFile = wshFSO.CreateTextFile(sFileLogPath & sFileLogName) objLogFile.Write("-----------------------------------------------------"& chr(13) & chr(10)) objLogFile.Write("*** STARTING BACKUP - " & sFileLogName & " ***" & chr(13) & chr(10)) objLogFile.Write("-----------------------------------------------------" & chr(13) & chr(10)) objLogFile.Write(chr(13) & chr(10)) If wshFSO.FileExists(sFileLoc) then Set objOutputFile = wshFSO.OpenTextFile(sFileLoc, ForReading) '---------------------- 'Loop though Servers '---------------------- Do While objOutputFile.AtEndOfStream <> True sServerName = objOutputFile.ReadLine sServerNameVCB = ucase(sServerName) & ".domainname.co.uk-FullVM" If len(sServerName) then preCMD = chr(34) & "C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\pre-backup.bat" & chr(34) & " VCB_" & sServerName & " " & Trim(sServerNameVCB) postCMD = chr(34) & "C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\post-backup.bat" & chr(34) & " VCB_" & sServerName objLogFile.Write("**************************************************************************************" & chr(13) & chr(10)) objLogFile.Write("** Starting BEMCMD Command to Backup to Tape ** ---> For Server " & Trim(sServerName ) & chr(13) & chr(10)) objLogFile.Write("**************************************************************************************" & chr(13) & chr(10)) objLogFile.Write("** Creating backup job script **" & chr(13) & chr(10)) 'Re-build the backupscript from the template wshFSO.CopyFile "C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\vcb_backup_job_template.txt", sBackupScript ,TRUE WriteINIString "General", "JOB_NAME", "VCB_" & sServerName , sBackupScript WriteINIString "Miscellaneous", "PRE_JOB_COMMAND", preCMD , sBackupScript WriteINIString "Miscellaneous", "POST_JOB_COMMAND", postCMD , sBackupScript WriteINIString "Selections", "PATH1", "d:\mnt\" & Trim(sServerNameVCB) & "\*.*" , sBackupScript objLogFile.Write(" General --> JobName = " & "VCB_" & sServerName & chr(13) & chr(10)) objLogFile.Write(" Miscellaneous --> PRE_JOB_COMMAND = " & preCMD & chr(13) & chr(10)) objLogFile.Write(" Miscellaneous --> POST_JOB_COMMAND = " & postCMD & chr(13) & chr(10)) objLogFile.Write(" Selections --> PATH1 = " & "d:\mnt\" & Trim(sServerNameVCB) & chr(13) & chr(10)) 'Delete any old selection lists for this server objLogFile.Write("** Deleting old Selection Lists" &chr(13) & chr(10)) BEMCMD_SEL_LIST = chr(34) & "c:\Program Files\Symantec\Backup Exec\bemcmd" & chr(34) &" -o221 -sVCB_" & sServerName objLogFile.Write("** About to run CMD: ---> " & BEMCMD_SEL_LIST &chr(13) & chr(10)) WshShell.Run BEMCMD_SEL_LIST, 1, TRUE 'Run the command 'Delete any old moint points for this server If wshFSO.FolderExists("d:\mnt\" & sServerNameVCB) Then wshFSO.DeleteFolder("d:\mnt\" & sServerNameVCB) End if 'Run BECMD Commmand and wait for it to complete BEMCMD = chr(34) & "c:\Program Files\Symantec\Backup Exec\bemcmd" & chr(34) &" -o90 -v -la:" & chr(34) & "C:\Logs\" & sFileLogName & chr(34) & " -w -f" & chr(34) & sBackupScript & chr(34) objLogFile.Write("** About to run the cmd: ---> " & BEMCMD &chr(13) & chr(10)) objLogFile.Write("** VMWare VCB Logs will be in: ---> C:\Logs\Vmware\" &chr(13) & chr(10)) objLogFile.Write("** Output from cmd to follow **" & chr(13) & chr(10)) objLogFile.Close WshShell.Run BEMCMD, 1, TRUE 'Run the command WshShell.Run BEMCMD_SEL_LIST, 1, TRUE 'Run the command Delete any old selection lists Set objLogFile = wshFSO.OpenTextFile(sFileLogPath & sFileLogName, ForAppending) objLogFile.Write("**************************************************************************************" & chr(13) & chr(10)) objLogFile.Write("** Ending BEMCMD Command to Backup to Tape ** ---> For Server " & Trim(sServerName ) & chr(13) & chr(10)) objLogFile.Write("**************************************************************************************" & chr(13) & chr(10)) Else objLogFile.Write("** WARNING ** ::: A Line in the file " & sFileLoc & " in blank." & chr(13) & chr(10)) End If Loop Else objLogFile.Write("** ERROR ** ::: An Error has occured the file " & sFileLoc & " (the list of servers) could not be found." & chr(13) & chr(10)) Cleanup End if CleanUp '---------------------------- 'Subs and Functions '---------------------------- Sub CleanUp objLogFile.Close Set objLogFile = wshFSO.OpenTextFile(sFileLogPath & sFileLogName, ForAppending) objLogFile.Write(chr(13) & chr(10)) objLogFile.Write("------------------------------------------------" & chr(13) & chr(10)) objLogFile.Write("*** ENDING BACKUP - " & now() & " ***" & chr(13) & chr(10)) objLogFile.Write("------------------------------------------------" & chr(13) & chr(10)) '--Called on exit-- objOutputFile.Close objLogFile.Close Set wshFSO = Nothing WScript.Quit(0) End Sub '---------------------------- 'Ini Files '---------------------------- Sub WriteINIStringVirtual(Section, KeyName, Value, FileName) WriteINIString Section, KeyName, Value, _ Server.MapPath(FileName) End Sub Function GetINIStringVirtual(Section, KeyName, Default, FileName) GetINIStringVirtual = GetINIString(Section, KeyName, Default, _ Server.MapPath(FileName)) End Function 'Work with INI files In VBS (ASP/WSH) 'v1.00 '2003 Antonin Foller, PSTRUH Software, http://www.motobit.com 'Function GetINIString(Section, KeyName, Default, FileName) 'Sub WriteINIString(Section, KeyName, Value, FileName) Sub WriteINIString(Section, KeyName, Value, FileName) Dim INIContents, PosSection, PosEndSection 'Get contents of the INI file As a string INIContents = GetFile(FileName) 'Find section PosSection = InStr(1, INIContents, "[" & Section & "]", vbTextCompare) If PosSection>0 Then 'Section exists. Find end of section PosEndSection = InStr(PosSection, INIContents, vbCrLf & "[") '?Is this last section? If PosEndSection = 0 Then PosEndSection = Len(INIContents)+1 'Separate section contents Dim OldsContents, NewsContents, Line Dim sKeyName, Found OldsContents = Mid(INIContents, PosSection, PosEndSection - PosSection) OldsContents = split(OldsContents, vbCrLf) 'Temp variable To find a Key sKeyName = LCase(KeyName & "=") 'Enumerate section lines For Each Line In OldsContents If LCase(Left(Line, Len(sKeyName))) = sKeyName Then Line = KeyName & "=" & Value Found = True End If NewsContents = NewsContents & Line & vbCrLf Next If isempty(Found) Then 'key Not found - add it at the end of section NewsContents = NewsContents & KeyName & "=" & Value Else 'remove last vbCrLf - the vbCrLf is at PosEndSection NewsContents = Left(NewsContents, Len(NewsContents) - 2) End If 'Combine pre-section, new section And post-section data. INIContents = Left(INIContents, PosSection-1) & _ NewsContents & Mid(INIContents, PosEndSection) else'if PosSection>0 Then 'Section Not found. Add section data at the end of file contents. If Right(INIContents, 2) <> vbCrLf And Len(INIContents)>0 Then INIContents = INIContents & vbCrLf End If INIContents = INIContents & "[" & Section & "]" & vbCrLf & _ KeyName & "=" & Value end if'if PosSection>0 Then WriteFile FileName, INIContents End Sub Function GetINIString(Section, KeyName, Default, FileName) Dim INIContents, PosSection, PosEndSection, sContents, Value, Found 'Get contents of the INI file As a string INIContents = GetFile(FileName) 'Find section PosSection = InStr(1, INIContents, "[" & Section & "]", vbTextCompare) If PosSection>0 Then 'Section exists. Find end of section PosEndSection = InStr(PosSection, INIContents, vbCrLf & "[") '?Is this last section? If PosEndSection = 0 Then PosEndSection = Len(INIContents)+1 'Separate section contents sContents = Mid(INIContents, PosSection, PosEndSection - PosSection) If InStr(1, sContents, vbCrLf & KeyName & "=", vbTextCompare)>0 Then Found = True 'Separate value of a key. Value = SeparateField(sContents, vbCrLf & KeyName & "=", vbCrLf) End If End If If isempty(Found) Then Value = Default GetINIString = Value End Function 'Separates one field between sStart And sEnd Function SeparateField(ByVal sFrom, ByVal sStart, ByVal sEnd) Dim PosB: PosB = InStr(1, sFrom, sStart, 1) If PosB > 0 Then PosB = PosB + Len(sStart) Dim PosE: PosE = InStr(PosB, sFrom, sEnd, 1) If PosE = 0 Then PosE = InStr(PosB, sFrom, vbCrLf, 1) If PosE = 0 Then PosE = Len(sFrom) + 1 SeparateField = Mid(sFrom, PosB, PosE - PosB) End If End Function 'File functions Function GetFile(ByVal FileName) Dim FS: Set FS = CreateObject("Scripting.FileSystemObject") 'Go To windows folder If full path Not specified. If InStr(FileName, ":\") = 0 And Left (FileName,2)<>"\\" Then FileName = FS.GetSpecialFolder(0) & "\" & FileName End If On Error Resume Next GetFile = FS.OpenTextFile(FileName).ReadAll End Function Function WriteFile(ByVal FileName, ByVal Contents) Dim FS: Set FS = CreateObject("Scripting.FileSystemObject") 'On Error Resume Next 'Go To windows folder If full path Not specified. If InStr(FileName, ":\") = 0 And Left (FileName,2)<>"\\" Then FileName = FS.GetSpecialFolder(0) & "\" & FileName End If Dim OutStream: Set OutStream = FS.OpenTextFile(FileName, 2, True) OutStream.Write Contents End Function
You will need to create a C:\Logs folder
/* BACKUP SCRIPT */ /* operations: 90 */
[General]
JOB_TYPE=Backup JOB_PRIORITY=MEDIUM
JOB_NAME=jobname
[Backup_Options] BK_METHOD=0
[Media_Options]
MEDIA_SET=VMware_VCB APPEND= 1 APPEND_NO_OVERWRITE=0 VERIFY=0 COMPRESSION_TYPE=2 EJECT_MEDIA=0
[Miscellaneous]
PRE_JOB_COMMAND=command POST_JOB_COMMAND=command
COMMAND_RUN_JOB_IF_PRE_SUCCESS=1 COMMAND_RUN_POST_IF_PRE_SUCCESS=1 COMMAND_RUN_POST_IF_JOB_FAILS=1 COMMAND_FAIL_JOB_IF_FAILS=1
COMMAND_AUTO_CANCEL_TIME=120
[Schedule] RUN_IMMEDIATE=YES
DELETE_JOB_AFTER=1
[Selections] PATH1=C:\test INCLUDE1=YES SUBDIRS1=YES
To run the script you could either create a windows scheduled task or as I did create a batch file that uses the “start” command to call the vbs file and then add that batch file to the pre-command section of a backup job in Backup Exec.
comments, improvements (very could be many) or question please post.
This script works great! Good work.
Glad it was of use, we are still using this script a year on and so far no problems.
I am interested by the new Backup Exec 12.5 Vmware agent, it seems like they have created their own GUI take on VCB but have not tried it yet.
Just updated our VCB server to version 1.5 update 1 and the script is still working with no changes
I recently upgraded our Backup Exec to version 13 "Backup Exec 2010" and still working no change required
Awesome script!! Works a bl**dy treat!!
I made a couple ‘mods’ (I hope you don’t mind) to the script as I needed to do the following:
– Target the BE device to be used.
– Send an email alert if the job failed or succeeded.
Targetting the BE device
As I use Hard Drives instead of Tape to backup data, I needed to backup the VMs to Backup-To-Disk folders , so I added the following:
Add a new sValue
sDeviceName = "Backup-To-Disk Folder Name"
Add the following lines, it’s fairly obvious where to put the below lines in the script.
WriteINIString "Backup_Options", "DEVICE_NAME", sDeviceName , sBackupScript
objLogFile.Write(" Backup Device –> = " & sDeviceName & chr(13) & chr(10))
Two pre-requisites for the above:
– In the template file – vcb_backup_job_template.txt – add DEVICE_NAME=device under the Backup_Options header.
– In BE make sure the backup-to-disk folder is created and configured.
Sending an Email Alert
Since the job will be run at night I wanted to get alerted by email if the job failed or succeeded, so I added following:
Add two new sValues – These values are written to the log file by bemcmd if the job fails or succeeds.
sVCBSuccess = "RETURN VALUE: 1"
sVCBFailed = "RETURN VALUE: -1"
Add the below between WshShell.Run BEMCMD_SEL_LIST, 1, True and Set objLogFile = wshFSO.OpenTextFile(sFileLogPath & sFileLogName, ForAppending)
Set objLogFile = wshFSO.OpenTextFile(sFileLogPath & sFileLogName, ForReading, -2)
Do While objLogFile.AtEndOfStream <> True
sReturn = objLogFile.ReadLine
If Trim(sReturn) = Trim(sVCBSuccess) Then
BUSuccessEmail()
Else If Trim(sReturn) = Trim(sVCBFailed) Then
BUFailedEmail()
End If
End If
Loop
Set objLogFile = Nothing – I set this as I wanted to make sure the log file was closed for the next write by the script.
You could create a sub but it’s only a few lines to add. I use two cdomail functions to generate and send the email alert.
I am glad you got some use out of it.
Thanks for posting the mods, I am loving the "Targetting the BE device" mod you have made.
Another solution for sending an email might be to configure your Backup Exec "Job Failed" alert so Backup Exec is sending the email.
P.s. Welcome to Geeks!!
If you like please feel free to contribute to the site by creating an article to share something that others would find useful, looks like you a pretty handy with the VBS :-)P
Just looked at BE and ah yea you can do blanket alerts for failures/successes. I usually use selection list for emailing alerts. I just thought I was being smart =)
Just a little improvment on an already great script.
I read this post completely concerning the comparison of newest and
earlier technologies, it’s awesome article.
Hi,
sorry when I´m too stupid and asking probably simple things.
I have donwloaded and installed VMware-vcb-226297.exe (the latest one) and installed in BE12.5.
I see the Folder added: C:\Program Files\VMware\VMware Consolidated Backup Framework
The zipped files from VMware-veritas-backupexec-integration-150805.zip i unzipp and put in the C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec.
Then i download all your scripts and put in the same folder where i unzipped the 150805.zip.
C:\LOGS is created and server_list.txt is editet.
The job_template.txt is copied and edited with the domainnaem-full-vm.
So far so good, teh scripts starts and report an error:
Getting list of backup-to-disk devices…
ERROR: Specified object not found.
Getting list of media sets…
After this it fails. I don´t see any reason why.
Any hints?
Tnx in advance
Hi,
Hope this helps;
– My scripts (all 4 files) need to go under c:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec\
– Add your servers into vcb_servers_list.txt as they appear in vmware
– You need to create C:\logs\ folder
– Edit run_vcb_backup.vbs to replace to Active Directory domain name
sServerNameVCB = ucase(sServerName) & ".domainname.co.uk-FullVM"
– In run_vcb_backup.vb do a find and replace for d:\mnt\ and replace with the location of your temporary mount point (this may be your problem)
– Make sure from a command prompt you can run c:\Program Files\Symantec\Backup Exec\bemcmd
– After that I would try forcing backup exec to use a certain drive (see below)
In run_vcb_backup.vb
After:
WriteINIString "Selections", "PATH1", "d:\mnt\" & Trim(sServerNameVCB) & "\*.*" , sBackupScript
Add:
WriteINIString "Backup_Options", "DEVICE_NAME", "Drive 2" , sBackupScript
After:
objLogFile.Write(" Selections –> PATH1 = " & "d:\mnt\" & Trim(sServerNameVCB) & chr(13) & chr(10))
Add:
objLogFile.Write(" Backup Device –> = " & "Drive 2" & chr(13) & chr(10))
In vcb_backup_job_template.txt
After:
BK_METHOD=0
Add:
DEVICE_NAME=device
Replacing Drive 2 with the name of your drive as it appears in Backup exec
Hi all,
the script looks good and but it won´t work for me.
I describe what i hvae done like i understood it.
-downloaded fron VM VMware-vcb-226297.exe and installed (can the the new folder: C:\Program Files\VMware\VMware Consolidated Backup Framework\
-extracted the VMware-veritas-backupexec-integration-150805.zip to C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec
-copied all the 4 scripts from the download to C:\Program Files\VMware\VMware Consolidated Backup Framework\backupexec
-created c:\logs
-edit vcb_server_list.txt with the netbiosname from a server
-changed in the vbs the part .domainname-full-vm
-the sdevicename="E:\VCB2" added in the job_template
-in the vbs-script adding: WriteINIString "Backup_Options", "DEVICE_NAME", sDeviceName , sBackupScript
objLogFile.Write(" Backup Device –> = " & sDeviceName & chr(13) & chr(10))
-Backup-ToDiskFolder is added like the netbiosname of the server.
vbs is starting an i get the follwing error found in logs is:
Getting list of backup-to-disk devices…
ERROR: Specified object not found.
Getting list of media sets…
Well, i don`t find annything where i can search further.
Tnx in advance for help.