VMware Cloud Community
bentech20111014
Contributor
Contributor

Storage VMotion 350+ Servers with 800+ associated vmdk files.

First I have to thank LucD and Avlieshout for their posts and help.

I was given a task of moving hundreds of systems to new nfs storage volumes.  And as usual it had to be done yestersday.  It worked out great and I was able to finish in about two weeks.  I figured I would share what I put together based on code posted by Avlieshout.

# ===============================================================
# SCRIPT NAME: svmotion.ps1
# AUTHOR:
# MANAGER:
# DATE:
# COMMENT:
# VERSION: 1.0
# REVISIONS:
# ===============================================================

Clear-Host
$vCenter = Read-Host 'Enter vCenter Server Name'
$name = Read-Host 'Enter Username [domain\Username]'
$pwd = Read-Host 'Enter Password'
Clear-Host
Connect-VIServer $vCenter -User $name -Password $pwd
Clear-Host

do {
Write-Host " "
$targetVM = Read-Host 'Enter Machine to SVMotion'
$vm = Get-VM $targetVM
Write-Host "*** SVMotion Script for $vm ***" -foregroundcolor Yellow
$response = Read-Host 'Enter Number of Hard Disks [1-4]'

switch ($response) {

1 {
$HardDisk1DatastoreName = Read-Host 'Enter "Hard Disk 1" Target Location '
$configDatastoreName = $HardDisk1DatastoreName

Write-Host "SVMotion Started for $vm " -ForegroundColor Red

$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = (Get-Datastore $configDatastoreName | Get-View).MoRef

#HardDisk 1
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[0].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk1DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#When all harddisks are specified call the RelocateVM_task()
$vm.ExtensionData.RelocateVM_Task($spec, "defaultPriority")
break
Clear-Host
}

2 {
$HardDisk1DatastoreName = Read-Host 'Enter "Hard Disk 1" Target Location '
$configDatastoreName = $HardDisk1DatastoreName
$HardDisk2DatastoreName = Read-Host 'Enter "Hard Disk 2" Target Location '
Write-Host "SVMotion Started for $vm " -ForegroundColor Red

$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = (Get-Datastore $configDatastoreName | Get-View).MoRef

#HardDisk 1
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[0].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk1DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#HardDisk 2
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[1].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk2DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#When all harddisks are specified call the RelocateVM_task()
$vm.ExtensionData.RelocateVM_Task($spec, "defaultPriority")
break
Clear-Host
}

3 {
$HardDisk1DatastoreName = Read-Host 'Enter "Hard Disk 1" Target Location '
$configDatastoreName = $HardDisk1DatastoreName
$HardDisk2DatastoreName = Read-Host 'Enter "Hard Disk 2" Target Location '
$HardDisk3DatastoreName = Read-Host 'Enter "Hard Disk 3" Target Location '
Write-Host "SVMotion Started for $vm " -ForegroundColor Red

$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = (Get-Datastore $configDatastoreName | Get-View).MoRef

#HardDisk 1
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[0].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk1DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#HardDisk 2
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[1].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk2DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#HardDisk 3
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[2].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk3DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#When all harddisks are specified call the RelocateVM_task()
$vm.ExtensionData.RelocateVM_Task($spec, "defaultPriority")
break
Clear-Host
}

4 {
$HardDisk1DatastoreName = Read-Host 'Enter "Hard Disk 1" Target Location '
$configDatastoreName = $HardDisk1DatastoreName
$HardDisk2DatastoreName = Read-Host 'Enter "Hard Disk 2" Target Location '
$HardDisk3DatastoreName = Read-Host 'Enter "Hard Disk 3" Target Location '
$HardDisk4DatastoreName = Read-Host 'Enter "Hard Disk 4" Target Location '
Write-Host "SVMotion Started for $vm " -ForegroundColor Red

$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = (Get-Datastore $configDatastoreName | Get-View).MoRef

#HardDisk 1
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[0].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk1DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#HardDisk 2
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[1].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk2DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#HardDisk 3
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[2].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk3DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#HardDisk 4
$objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
$objDisk.DiskID = $vm.HardDisks[3].Id.Split('/')[1]
$objDisk.DataStore = (Get-Datastore $HardDisk4DatastoreName | Get-View).MoRef
$spec.Disk += $objDisk

#When all harddisks are specified call the RelocateVM_task()
$vm.ExtensionData.RelocateVM_Task($spec, "defaultPriority")
break
Clear-Host
}

0 {
Write-Host "Exiting Script"
break
}

default {
"** The selection could not be determined **"
break
}
}
}
while ($response -ne "0")

Reply
0 Kudos
5 Replies
avlieshout
VMware Employee
VMware Employee

Thank you for sharing and glad to hear that everything worked out fine!

Arnim

Arnim van Lieshout Blogging: http://www.van-lieshout.com Twitter: http://www.twitter.com/avlieshout If you find this information useful, please award points for "correct" or "helpful".
Reply
0 Kudos
bentech20111014
Contributor
Contributor

Hi Arnim, again I can't thank you enough for all the help you provided me via this community.

The script mentioned here, based on your code, worked like a charm as I mentioned; however, I just upgraded to the latest version of PowerCLI (VMware-PowerCLI-4.1.1-332441) and now the script doesn't work due to obsolete property.

Here is the error:

WARNING: 'HardDisks' property is obsolete. Use 'Get-HardDisk' cmdlet instead.
Exception calling "RelocateVM_Task" with "2" argument(s): "Not initialized: vim.Datastore datastore"
At C:\scripts\svmotion.ps1:45 char:34
+ $vm.ExtensionData.RelocateVM_Task <<<< ($spec, "defaultPriority")
    + CategoryInfo          : NotSpecified: (:) [], MethodInvocationException
    + FullyQualifiedErrorId : DotNetMethodException

I'm hoping it's a small change.

Thank you very much,

Robert

Reply
0 Kudos
LucD
Leadership
Leadership

Hi Robert,

There are in fact 2 different messages.

The first one is a warning about the Harddisks property, which is annoying but doesn't make your script fail.

The 2nd on says that the datastore property in the $spec variable is not initialised properly.

Could it be that the first datastore name you entered was incorrect by any chance ?

I tested it and for me it all works.


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

Reply
0 Kudos
LucD
Leadership
Leadership

I made some changes to your script to avoid the warning and to use the PowerCLI 4.1u1 features

# ===============================================================
# SCRIPT NAME: svmotion.ps1
# AUTHOR:
#
MANAGER:
# DATE:
#
COMMENT:
# VERSION: 1.0
#
REVISIONS:
#
===============================================================
Clear-Host
$vCenter
= Read-Host 'Enter vCenter Server Name'
$name = Read-Host 'Enter Username [domain\Username]'
$pwd = Read-Host 'Enter Password'
Clear-Host

Connect-VIServer
$vCenter -User $name -Password $pwd
Clear-Host do {     Write-Host " "
    $targetVM = Read-Host 'Enter Machine to SVMotion (q to quit)'
    if($targetVM -ne "q"){         $vm = Get-VM $targetVM
       
Write-Host "*** SVMotion Script for $vm ***" -foregroundcolor Yellow
        $HardDisks = @(Get-HardDisk -VM $vm)         Write-Host "SVMotion Started for $vm " -ForegroundColor Red
       
$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
       
1..$HardDisks.Count | %{             $dsName = Read-Host ('Enter "Hard Disk ' + $_ + '" Target Location ')             if($_ -eq 1){                 $spec.Datastore = (Get-Datastore $dsName).Extensiondata.MoRef             }             $objDisk = New-Object VMware.Vim.VirtualMachineRelocateSpecDiskLocator
            $objDisk.DiskID = $HardDisks[$_ - 1].Id.Split('/')[1]             $objDisk.DataStore = (Get-Datastore $dsName).Extensiondata.MoRef             $spec.Disk += $objDisk        }         $vm.ExtensionData.RelocateVM_Task($spec, "defaultPriority")         Clear-Host
    } } until($targetVM -eq "q")


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

Reply
0 Kudos
bentech20111014
Contributor
Contributor

LucD, thank you for helping me out yet again.  The improvements you made to the script are perfect.  The one big thing lacking from the old version was having the guest disk count prior to execution.  What a time saver.  Awesome!

Reply
0 Kudos