I have a script that performs a space check prior to cloning some VM's onto a datastore. Sometimes it appears to fail (well it exits by design) and behaves as if there was insufficient space. If however I manually refresh the datastore properties by clicking the button shown in the screenshot prior it sppears to work consistently. Can someone please provide an example if how I can essentially press this button for a specific datastore in PowerCLi so I can incorperate it into my script.
Thanks
The following should do the same as the button.
The Get-Datastore cmdlet gets the info from the vSphere object.
Due to performance reasons that info is refreshed on intervals, or when you explicitly ask for a refresh.
$ds.ExtensionData.RefreshDatastoreStorageInfo()
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
And if anyone has any insight or even a theory as to why this might be happening I would appreciate your opinion, below is an example of the script...
# ==============================================================================================
# NAME: RecoverVMs
#
# AUTHOR: Luke Glazebrook
# DATE : 09/10/2015
#
# COMMENT: Recovers cloned VMs and uses passed param to specify which cycle of VMs to restore,
# and removes the -$CYRPYYMMDD ammendment at the end of the VM name.
#
#
#
# * Software Dependencies: *
# - Microsoft PowerShell *
# - VMWare PowerCLI *
# ==============================================================================================
# Parameters
# ==============================================================================================
# The below parameter supplied by Control-M refers to cycle and recovery point prefix,
# the date can be added automatically however this functionality has been disabled.
param ([string]$CYRPYYMMDD)
# ==============================================================================================
# Functions
# ==============================================================================================
#Function to allow you to check if a command is loaded
Function Check-Command($cmdname)
{
return [bool](Get-Command -Name $cmdname -ErrorAction SilentlyContinue)
}
# ==============================================================================================
# Varibles
# ==============================================================================================
# Add the vmware snapin for powershell
# Add-PSSnapin VMware.VimAutomation.Core
# Add the vmware snapin for powershell (stops you seeing the error messages)
if (Check-Command "Connect-VIServer")
{
Write-Host "Automation Tool already loaded"
}
else
{
#If not already loaded load the snapin
Write-Host "Loading Automation Tools"
Add-PSSnapin VMware.VimAutomation.Core
}
# backup = true appends date; false creates a clone with the same name.
$backup = "True"
# debug - true : will not clone vm; FALSE will clone the vm.
$debug = "FALSE"
# Target Datastore
$targetdatastore = "LS-H249-DS1-320GB"
#Refers to the percentage of free space for the DS space check
$freePerc = 5
# Target location - existing folder in vcenter structure, where the clones will be place
$targetlocation = "ProdFolder"
# Set date
$datestart = (get-date -uformat %Y%m%d)
# Name a logfile to capture results.
$logfile = $datestart + "_VMClones_bulk.txt"
#
write-output "New Log ($datestart) - ($logfile)" >> $logfile
# Gets the list of VMs from the file associated with this script
$VmFileList = Get-Content VmsToCloneList.list
#
$ds = Get-Datastore -Name $targetdatastore
#Email varibles
$From = "vCenter@lbase.homeip.net"
$To = "luke@lbase.homeip.net"
$Cc = "luke@lbase.homeip.net"
#$Attachment = "C:\temp\Some random file.txt"
$Subject = "!! TEST DMAT Report TEST !!"
$BodySuccess = "The DMAT VMs have been sucessfully recovered to the specified destination datastore and inventory organisational folder within vSphere"
$BodyFailure1 = "The combined provisioned VMDK usage of the VM's exceeds the capacity of the destination datastore, exiting with code 1"
$BodyFailure2 = "There is insufficient space on the target datastore, increase Space to continue, Exiting with code 2"
$BodyFailure3 = "A VM by the name specified cant be found perhaps it does not exists? Exiting with code 3"
$SMTPServer = "192.168.0.101"
$SMTPPort = "25"
# Establish Connection
Connect-VIServer -Server 127.0.0.1 -User administrator@blah -Password blah
# ==============================================================================================
# Deletes current working test VMs in preperation for the recovery of the backup clones
# ==============================================================================================
foreach($vm in $VmFileList){
$active = Get-VM $vm
if($active.PowerState -eq "PoweredOn"){
Stop-VM -VM $vm -Confirm:$false
Start-Sleep -Seconds 10
Remove-VM -VM $vm -DeleteFromDisk -Confirm:$false -RunAsync}
else
{Remove-VM -VM $vm -DeleteFromDisk -Confirm:$false -RunAsync}
}
# ==============================================================================================
# Gets the VM total ProvisionedSpaceGB for all VM's in the list.
# Additionally ensures whitespaces and hashes are ignored effectively
# creating a clean list which calculates/creates the varible required for validation check 1
# ==============================================================================================
$vmCleanedList = New-Object system.Collections.ArrayList
# Loop through our VM file List and clean is up, check for incorrectly specified VM's
ForEach ($vmname in $VmFileList)
{
if ([string]::IsNullOrWhiteSpace($vmname) -or $vmname.StartsWith("#"))
{
write-host("Invalid machine name - $vmname")
}
else
{
#Should trim vmname to ensure we have no spaces front or end
$vm = Get-VM $vmname
$vmCleanedList.Add($vmname)
$TotalRequiredGB += $vm.ProvisionedSpaceGB
}
Write-Host "Total Required = $TotalRequiredGB"
}
# ==============================================================================================
# Validation checks Prior to starting the clone script
# ==============================================================================================
# Validation check 1, Checks if the combined provisioned VMDK usage of the VM's exceeds the capacity of the destination datastore?
if(($ds.FreeSpaceGB -gt $TotalRequiredGB))
{
Write-Host "Continue with your script"
}
else
{
Write-Host "There is insufficient space on the target datastore. Please increase Space to continue"
Write-Output "There is insufficient space on the target datastore. Please increase Space to continue" >> $logfile
Write-Host "Exiting with code 1"
Write-Output "Exiting with code 1" >> $logfile
Send-MailMessage -From $From -to $To -Cc $Cc -Subject $Subject `
-Body $BodyFailure1 -SmtpServer $SMTPServer -port $SMTPPort
exit 1
}
$ds = Get-Datastore -Name $targetdatastore
# Validation check 2, do you have X % free datatstorespace?
if(($ds.FreeSpaceGB/$ds.CapacityGB*100) -ge $freePerc)
{
Write-Host "Continue with your script"
}
else
{
Write-Host "There is less than X% space free on the datastore. Please increase Space to continue"
Write-Output "There is less than X% space free on the datastore. Please increase Space to continue" >> $logfile
Write-Host "Exiting with code 2"
Write-Output "Exiting with code 2" >> $logfile
Send-MailMessage -From $From -to $To -Cc $Cc -Subject $Subject `
-Body $BodyFailure2 -SmtpServer $SMTPServer -port $SMTPPort
exit 2
}
#Hack + duplication of effort
#$VmListFile = Get-Content VmsToCloneList.list | Select-Object -Skip 3
ForEach ($vmname in $vmCleanedList)
{
# The VM Object
$RemoveCYRPYYMMDD = $vmname + "-" + $CYRPYYMMDD
$vm = Get-VM -Name $RemoveCYRPYYMMDD
# Target Host - use the same host as the current VM ( this is faster than cloning across hosts ).
$targethost = $vm.vmhost.name
# Target VM Name - name if BACKUP is FALSE
$vmtarget = $vmname
#
$datastore = get-datastore $targetdatastore -vmhost $targethost
# ==============================================================================================
# Begin the actual cloning script
# ==============================================================================================
if ($vm -ne $null)
{
Write-Host "A VM named $VM exists. Starting clone"
Write-output "A VM named $VM exists. Starting clone" >> $logfile
}
else
{
Write-Host "A VM by the name specified cant be found perhaps it does not exists?"
Write-Output "A VM by the name specified cant be found perhaps it does not exists?" >> $logfile
Write-Host "Exiting with code 3"
Write-Output "Exiting with code 3" >> $logfile
Send-MailMessage -From $From -to $To -Cc $Cc -Subject $Subject `
-Body $BodyFailure3 -SmtpServer $SMTPServer -port $SMTPPort
exit 3
}
if ($backup -eq "TRUE")
{
# Clone the VM to backup_vmname_todaysdate
$vmtarget #= $vmtarget + "-" + $CYRPYYMMDD #+ "-" + $datestart
}
# nice colors if you are watching the script run
write-host -foregroundcolor green "Cloning $vm to $vmtarget"
write-output -foregroundcolor green "Cloning $vm to $vmtarget" >> $logfile
new-vm -name $vmtarget -vm $vm -vmhost $targethost -datastore $datastore -Location $targetlocation -DiskStorageFormat thin
Send-MailMessage -From $From -to $To -Cc $Cc -Subject $Subject `
-Body $BodySuccess -SmtpServer $SMTPServer -port $SMTPPort
}
Write-Host "Complete"
Exit 0
# COMPLETED
The following should do the same as the button.
The Get-Datastore cmdlet gets the info from the vSphere object.
Due to performance reasons that info is refreshed on intervals, or when you explicitly ask for a refresh.
$ds.ExtensionData.RefreshDatastoreStorageInfo()
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Oh thankyou mate I super grateful
I have a follow up question if your around mate, the script seems to work great now. Just one strange issue, on rare occasions during testing the script will begin cloning all machines simultaneously rather than one by one. Are you able to speculate why that might occasionally happen? Hope you you had a nice Xmas incidentally assuming that's something you celebrate, unfortunately I was working
Strange that you see that happening, the New-VM cmdlet doesn't have a RunAsync switch, so the cmdlet should wait before firing off the next one.
The number of operations that can run in parallel is depending on the vSphere version.
See KB1003497
We had a nice meal with the family, nothing too fancy.
But it was nice
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference