jump to navigation

VMware VCB Backup Script March 8, 2011

Posted by General Zod in Backup, Tech, VMware.
trackback

Back in October 2009, my crew at work had implemented VMware Consolidated Backup [VCB] as our solution for backing up virtual machines.  Since it was a command line driven solution, I’d accepted the challenge of scripting a solution to automate the backups.  Now, the solution that was developed may not be the most efficient method out there, but we still leverage the solution today because the more recent VMware Data Recovery [vDR] appliance just is not as reliable as we would like it to be.

I’m going to tell you about the VCB solution that we currently have in-place, and you’re more than welcome to adapt the following for use in your own environment.  However, please keep in mind the following two blurbs…


I do not write my solutions for the non-technical individuals.  I’m going to assume that you have a working knowledge of the products discussed, or at least have the ability to do a little skull-sweat to figure out the necessary details.  It would be impossible to design full-proof instructions that would accommodate everyone, so I do not attempt to do so.  However, I am always willing to take a  stab at answering any questions that someone might pose.

and

WARNING:  If anything goes wrong with your implementation of the following example, then I will not accept responsibility for any data loss that you may incur.  Use the following details at your own risk.

With that out of the way, let’s get started…

 

The Hardware

Before we get started, I’m going to assume that you already have a tape backup solution in-place, and that you can easily add another piece of hardware into that mix.  You’re going to need a destination to dump the VCB backups to, so build a new server and add it into your tape backup solution.

My opted for a physical server to dedicate to my VCB backups because I’m running shy on SAN space, and I do not wish to waste the SAN space on backups.  Unfortunately, this does mean that I’ll be performing my VCB dumps across the network… however, as I do them one-at-a-time, it won’t generate too much traffic.

For my environment, we have a HP ProLiant DL380 G6 with two disk arrays.  The first array is a mirrored pair of 72 GB drives for the storage of the system partition.  The second is a series of six 146 GB drives in a RAID 5 array, which is partitioned into a single volume to server as the destination for our VCB backups.  It is on this server that VMware VCB is actually installed as well (not on the vCenter server).

 

The Scripts

There are technically 2 scripts used in this solution.  The first that I will talk about is a VCB.VBS file that launches the VCB backups.  The other script is a LAUNCH.CMD file which calls the VBS script each day.  You’ll need to store both of these script files into the same folder on the server where you have VCB installed.

Before you begin editing the scripts to suit your environment, you’re going to need to gather the following information.

  • The folder path to where the VCB executables were installed.
  • The folder path to where your scripts are stored.
  • The folder path to the target destination for the backup dumps.
  • The Username and Password of a Service account that has access to both your vCenter server and the backup destination.
  • The number of days you wish to store the VCB backups in the destination.
  • If you desire to use email alerts to inform you of when your backups are completed, then you’ll also need a TO and FROM address to use… and the hostname to your local SMTP relay server.

You’ll be updating this information into the “Global Constants” section of the VBS script.  For your convenience, I’ve highlighted these points in BOLD GREEN in the script below.

 

The VCB.VBS script

In summary, this script acquires the vCenter and VM hostnames from command line arguments, purges any old backups from your destination server, references the vCenter, backups up the VM, and sends an email report.  (Additionally, if the “testing” Boolean variable is set to TRUE, then it will display various messages on the screen for testing / demo purposes.)

 

‘ VCB.VBS by Zod — 10/26/09

‘ **************************************************
‘ Initialize Global Constants
‘ **************************************************

const testing = false                      ‘ Set to True for Alerts while Testing

if testing then wscript.echo "Initializing Constants and Variables"

const svcusername=”<service account username>"
const svcpassword="<service account password>"

const purge_days = -2                 ‘ Number of Days to Store VCB backups

‘ Local folder paths on vCenter Server
const path_work="C:\Source\VCB_Script\"
const path_vcb="C:\Program Files (x86)\VMware\VMware Consolidated Backup Framework\"
const path_backup="D:\vcb_backup\"
const log_filename="vcb_backup.log"

‘ Setup File management object
Set fso = CreateObject("Scripting.FileSystemObject")  

‘ Setup Command Run object
Dim WshShell, ExecCommand
Set WshShell = CreateObject("WScript.Shell")

‘ Constants for Email Reporting
const email_smtp="smtp.company.com"
const email_from=”alert@company.com
const email_to=”you@company.com
email_subject=""
email_body=""

‘ Variables for Documenting Disk Usage
disk_letter=""
disk_total_space=0
disk_free_space=0
disk_folder_list=""
const gb_convert=1073741824

‘ **************************************************
‘ Get Command Line Arguments
‘ **************************************************
if testing then wscript.echo "Get Command Line Arguments"

Set args = WScript.Arguments

if args.count < 1 then                    ‘ Confirm Hostname argument is present
   call log_file("Backup was not run.  VM Hostname was Missing.")
   call exit_script
end if

vcenter = args.Item(0)                    ‘ Get vCenter Hostname
vm_hostname = args.Item(1)          ‘ Get Hostname of VM

if testing then wscript.echo "VCENTER = " & vcenter
if testing then wscript.echo "VM_HOSTNAME = " & vm_hostname

‘ **************************************************
‘ Delete any Backups older than PURGE_DAYS old.
‘ **************************************************
if testing then wscript.echo "Delete any VCB Backups older than PURGE_DAYS old"

Set f = fso.GetFolder(path_backup)
drop_date = DateAdd("d", purge_days, Date)
Set sf = f.SubFolders
For Each f In sf
    If f.DateCreated < drop_date Then
       call log_file("Purging old folder: " & f.name)
       f.Delete
    End If
Next

‘ **************************************************
‘ Delete Folder containing same VM Hostname
‘ **************************************************
if testing then wscript.echo "Delete Folder containing old backup of same VM Hostname"

If fso.FolderExists(path_backup & vm_hostname) Then
   fso.deletefolder(path_backup & vm_hostname)
   call log_file(path_backup & vm_hostname & "\ folder was deleted prior to backup with same Hostname.")
End If

‘ **************************************************
‘ Acquire Managed Object Reference (MoRef) string
‘ **************************************************
if testing then wscript.echo "Acquire MoRef string"

Set MoRef_Code = NOTHING           ‘ Blank out the MoRef_Code variable

‘Run the VCBVMNAME command to extract the MoRef code from the Output.

if testing then wscript.echo "Run the VCBVMNAME command to extract the MoRef code"

WshShell.CurrentDirectory = path_vcb
Set ExecCommand = WshShell.Exec("vcbvmname -h " & vcenter & " -u " & svcusername & " -p " & svcpassword & " -s Name:" & vm_hostname)

While Not ExecCommand.StdOut.AtEndOfStream       ‘ While – End of Output
   OutputString = ExecCommand.StdOut.Readline()  ‘ Store each line of Output
   If instr(OutputString,"moref:") > 0 then      ‘ If "moref:" is in the text
      MoRef_Code = Mid(OutputString,7)
      if testing then wscript.echo "MoRef Code = " & MoRef_Code
   End if
   Do While ExecCommand.Status = 0    ‘ Loop until Command is Completed
      WScript.Sleep 100                            ‘ Wait 100 milliseconds
   Loop
Wend                                                     ‘ End While – End of Output
Set ExecCommand = NOTHING

‘ **************************************************
‘ Backup the VM
‘ **************************************************
if testing then wscript.echo "Backup the VM"

if testing then wscript.echo "Listing Variables:"
if testing then wscript.echo "vCenter = " & vcenter
if testing then wscript.echo "svcusername = " & svcusername
if testing then wscript.echo "Password = " & svcpassword
if testing then wscript.echo "MoRef Code = " & moref_code
if testing then wscript.echo "Path Backup = " & path_backup
if testing then wscript.echo "VM Hostname = " & vm_hostname

call log_file("Backup of " & vm_hostname & " initiated.")

WshShell.CurrentDirectory = path_vcb

‘Run VCBMOUNTER to backup the VM to the PATH_BACKUP path.
Set ExecCommand = WshShell.Exec("vcbmounter -h " & vcenter & " -u " & svcusername & " -p " & svcpassword & " -a moref:" & moref_code & " -r " & path_backup & vm_hostname & " -t fullvm -m nbd")

‘While Not ExecCommand.StdOut.AtEndOfStream       ‘ While – End of Output
   Do While ExecCommand.Status = 0       ‘ Loop until Command is Completed
      WScript.Sleep 100                               ‘ Wait 100 milliseconds
   Loop

‘Wend                                                        ‘ End While – End of Output
Set ExecCommand = NOTHING

call log_file("Backup of " & vm_hostname & " completed.")

‘ **************************************************
‘ Prepare details for Email Report
‘ **************************************************
if testing then wscript.echo "Prepare details for Email Report"

disk_letter=left(path_backup,1)     ‘ Get the Drive Letter in <path_backup>
set drive = fso.getdrive(disk_letter)            ‘ Get Drive information

‘ Get Total and Free Disk Space, and convert to GBs.
disk_total_space=round((drive.totalsize/gb_convert),2)
disk_free_space=round((drive.freespace/gb_convert),2)

email_subject="VCB: " & vm_hostname

‘ Populate the text that will make up the Body of the Email
email_body="From: " & vcenter & vbcrlf
email_body=email_body & disk_letter & ": has " & disk_free_space & " GB free out of a total " & disk_total_space & " GB." & vbcrlf & vbcrlf
email_body=email_body & "Usage in Backup Folder: " & path_backup & vbcrlf

‘ Write entry to Email Body for each subfolder in the <path_backup> folder.
Set f = fso.GetFolder(path_backup)
Set sf = f.SubFolders
For Each f In sf
   email_body=email_body & f.name & " was created on " & f.datecreated & " and uses " & round((f.size/gb_convert),2) & " GB" & vbcrlf
Next

if testing then wscript.echo "Send the Email Report"
call email_report                                ‘ Send disk usage report via SMTP email

if testing then wscript.echo "Exit Script"
call exit_script                                 ‘ Exit the Script

‘ **************************************************
‘ Send Report via SMTP Email
‘ **************************************************
Sub email_report
   Set objEmail = CreateObject("CDO.Message")
   objEmail.From = email_from
   objEmail.To = email_to
   objEmail.Subject = email_subject
   objEmail.Textbody = email_body
   objEmail.Configuration.Fields.Item("
http://schemas.microsoft.com/cdo/configuration/sendusing") = 2
   objEmail.Configuration.Fields.Item("
http://schemas.microsoft.com/cdo/configuration/smtpserver") = email_smtp
   objEmail.Configuration.Fields.Item("
http://schemas.microsoft.com/cdo/configuration/smtpserverport") = 25
   objEmail.Configuration.Fields.Update
   objEmail.Send
End Sub

‘ **************************************************
‘ Write to Log File
‘ **************************************************

Sub Log_File(entry_text)                         ‘ Write entry into VCB log file
   dim log_file
   log_entry = Date & ", " & Time & " — " & entry_text    ‘ Compose Log entry
   log_path = path_work & log_filename           ‘ Set path to the Log file
   set log_file = fso.opentextfile(log_path, 8, true)      ‘ Open the Log file
   log_file.writeline(log_entry)                ‘ Write to the Log file
   log_file.close                               ‘ Close the Log file
End Sub                                          ‘ End Sub Log_File

‘ **************************************************
‘ Terminate the Script
‘ **************************************************

Sub Exit_Script                         ‘ Write entry into VCB log file
   WScript.quit                                  ‘ Exit Script
End Sub                                          ‘ End Sub Log_File

 

PHEW!!!  Well, that’s the first script.  Don’t worry though, the 2nd script isn’t quite that involved.

 

The LAUNCH.CMD Script

This is the script that you’ll be launching daily via your Scheduled Task Manager on your Windows server.  All this script does is… check to see what day of the month it is, and then call the VCB.VBS script as needed depending upon which day it is.

Note that the calling of the VCB.VBS requires that you append the vCenter server hostname and the VM name to be backed up to the end of the line.  This is to allow you to perform backups against multiple vCenter servers should you require to do so.  (Most folks will only have 1 vCenter server.  My environment has 4 separate vCenter servers… don’t ask.)

As this is going to be the biggest manual part of the solution, it will require some occasional updating on your part.  I recommend that you review which VMs you desire to backup at least once a month, and update the LAUNCH.CMD script accordingly.

Please note that backups are only performed on days 1 thru 28 of each month.  As days 29, 30, and 31 are NOT necessarily going to occur each month.

 

@echo off

:: LAUNCH.CMD by Zod – 10/26/09

C:
cd "C:\Program Files (x86)\VMware\VMware Consolidated Backup Framework"

:: Get Day of the Month
setlocal
set select=
for /f "tokens=3 eol=/ delims=/ " %%A in (‘date /t’) do set select=%%A

:: Case to Appropriate VCB Backup launches
if "%select%"=="01" goto day01
if "%select%"=="02" goto day02
if "%select%"=="03" goto day03
if "%select%"=="04" goto day04
if "%select%"=="05" goto day05
if "%select%"=="06" goto day06
if "%select%"=="07" goto day07
if "%select%"=="08" goto day08
if "%select%"=="09" goto day09
if "%select%"=="10" goto day10
if "%select%"=="11" goto day11
if "%select%"=="12" goto day12
if "%select%"=="13" goto day13
if "%select%"=="14" goto day14
if "%select%"=="15" goto day15
if "%select%"=="16" goto day16
if "%select%"=="17" goto day17
if "%select%"=="18" goto day18
if "%select%"=="19" goto day19
if "%select%"=="20" goto day20
if "%select%"=="21" goto day21
if "%select%"=="22" goto day22
if "%select%"=="23" goto day23
if "%select%"=="24" goto day24
if "%select%"=="25" goto day25
if "%select%"=="26" goto day26
if "%select%"=="27" goto day27
if "%select%"=="28" goto day28
if "%select%"=="29" goto NoRun
if "%select%"=="30" goto NoRun
if "%select%"=="31" goto NoRun
goto end

:: Usage:  cscript C:\Script_Path\vcb.vbs <vcenter server> <vm name>

:: ****************************************
:day01
:: ****************************************
echo Day 01
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#1
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#2
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#3
goto end

:: ****************************************
:day02
:: ****************************************
echo Day 02

cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#4
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#5
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#6
goto end

:: ****************************************
:day03
:: ****************************************
echo Day 03

cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#7
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#8
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#9
goto end

ETC, ETC, ETC, Until…

:: ****************************************
:day28
:: ****************************************
echo Day 28
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#82
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#83
cscript C:\Script_Path\vcb.vbs vcenter_hostname vm_name_#84
goto end

:: ****************************************
:NoRun
:: ****************************************
echo No backups will be run today.
goto end

:: ****************************************
:end

Comments»

1. Gary - September 12, 2011

This is just what I was looking for. I have a bat script that does this but it’s not as robust. However…

I can’t get the vcbmounter part working correctly. It starts creating the log files, etc, but doesn’t start writing the vmdk 2gb chunck files. It just sits there.

I see that the output from vcbmounter is not displayed to the screen so I can’t check it. I tried adding >>[logfile] to the end but that didn’t work.

Also, I noticed you commented out the while/wend arround the vcbmounter statement, why?

I’m not that great at vbscript yet, I’m a UNIX guy, so any help you could provide would be appreciated. If I can get this to work it will be great!

Thanks!

2. Gary - September 12, 2011

I don’t know why the exec command stalled out but I was able to get this to work with the following:

dim cmdstr

cmdstr = “vcbmounter -h ” & vcenter & ” -u ” & svcusername & ” -p ” & svcpassword & ” -a ipaddr:” & vm_hostname & ” -r ” & path_backup & vm_hostname & “_vmdk -t fullvm”

return = WshShell.Run(cmdstr, 1, True)

if return >0 then

end if

This will open vcbmounter in a new shell where I can monitor the output. Or, if I want, I can use 0 instead of 1, to make it run in the background.

The “, True” makes the calling vbs script wait until vcbmounter has run, thus allowing me to trap errors in “return”.

Note also that I don’t need to get moref first if I use ipaddr.


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: