Hey all..
With a VM powered off, I'm trying to migrate a VM between datacenters within the same vCenter. There's no shared storage, different networks at the destination host. The GUI works (shows warning about missing network at destination), yet move-vm doesn't work between datacenters.
Trying: move-vm -vm test-20150309 -destination esx1 -datastore datastore1, I get the error:
move-vm : 3/9/2015 2:48:20 PM Move-VM Destination container must be in the same Datacenter.
At line:1 char:1
+ move-vm -vm test-20150309 -destination esx1. ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidArgument: (esx1:VMHostImpl) [Move-VM], VimException
+ FullyQualifiedErrorId : Client20_VmHostServiceImpl_CheckMoveVmParameters_InvalidDatacenter,VMware.VimAutomation.
ViCore.Cmdlets.Commands.MoveVM
The manual states -Destination can be folder,host,cluster etc.. Since hosts AND folders are bound by datacenters, I'm guessing it needs to know the new host & new folder. I've tried to use -destination twice, and I've tried -destination host,folder.
Move-VM : Cannot bind parameter because parameter 'Destination' is specified more than once. To provide multiple values to parameters that can accept multiple values, use the array syntax. For example, "-parameter value1,value2,value3".
Move-VM : Missing an argument for parameter 'Destination'. Specify a parameter of type 'VMware.VimAutomation.ViCore.Types.V1.Inventory.VIContainer' and try again.
I'm using PowerCLI 5.8, and tried on vCenter 5.0 and 4.0.
move-vm : 3/9/2015 2:48:20 PM Move-VM Destination container must be in the same Datacenter.
At line:1 char:1
+ move-vm -vm test-20150309 -destination esx1. ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidArgument: (esx1:VMHostImpl) [Move-VM], VimException
+ FullyQualifiedErrorId : Client20_VmHostServiceImpl_CheckMoveVmParameters_InvalidDatacenter,VMware.VimAutomation.
ViCore.Cmdlets.Commands.MoveVM
Does the SDK method work ?
See 3. Re: moving vm to a different datacenter
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Does the SDK method work ?
See 3. Re: moving vm to a different datacenter
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Hi Luc.
Thanks for the quick response. I appreciate the work you put in here.
RelocateVM as you pointed to did the trick.
For anyone else, I had to make a few changes for my environment, to cater for the default resource pool in that cluster.
$vmName = "TestVM"
$tgtDatastore = "datastore"
$tgtCluster = "cluster"
$tgtPool = "Resources" # "Resources" is the default resource pool
$vm = Get-VM -Name $vmName
$ds = Get-Datastore -Name $tgtDatastore
$esx = Get-Cluster -Name $tgtCluster | Get-VMHost | Get-Random
$rp = Get-ResourcePool -Name $tgtPool -Location $tgtCluster # Specify Cluster as there's multiple clusters with default resource pools in this vCenter.
$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = $ds.ExtensionData.MoRef
$spec.Host = $esx.ExtensionData.MoRef
$spec.Pool = $rp.ExtensionData.MoRef
$vm.ExtensionData.RelocateVM($spec,"defaultPriority")
* Note: I've tested this works on vCenter 5.0/4.0 all the way down to ESX 2.5.5.
I tried the help daunce through Twitter earlier and I was thrown off by the fact that the Move-VM cmdlet documentation states that you can give a datacenter as a VIContainer object to the -Destination parameter. It appears this might be inaccurate if he's got to use .NET properties.
--j
It depends on the vCenter version afaik
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
That's odd. I could have sworn the first Google link I hit for Move-VM ended up on the 4.1 Update 1 PowerCLI (which made me think vCenter 4.1) reference guide and it had the same sentence in it that the 5.8 guide had.
Either way, neither here nor there. It's not like documentation has ever been 100% accurate with any product I've ever worked with.
I picked up LucD's Script and created a whole Migration workflow with a simple placement decision:
Script – vSphere VM zwischen Datacenter verlagern | my cloud-(r)evolution
Hello,
I know this is an older post, but I'm trying to migrate powered off VMs with PowerCLI on the same vCenter from one cluster to another in different datacenters. I'm using the exact method Luc provided with the SDK but am getting the following error:
Exception setting "Pool": "Cannot convert the "System.Object[]" value of type "System.Object[]" to type "VMware.Vim.ManagedObjectReference"."
Here is my code:
$VM = Get-VM -Name $vmName
$RP = Get-ResourcePool -Name "Resources" -Location $cluster
$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = $newDS.ExtensionData.MoRef
$spec.Host = $newHost.ExtensionData.MoRef
$spec.Pool = $RP.ExtensionData.MoRef
$VM.ExtensionData.RelocateVM($spec,"defaultPriority")
vCenter is on 6.0 Update 2
Anyone have any thoughts? Been scratching my head with this one all morning.
Thanks in advance!
-Jason
That error indicates that you have provided an array (multiple objects) instead of a single object.
For one or another reason you have more than one object in $RP
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
LucD I have similar errors. Can you help me solve my errors?
$vmName = "MYVM"
$tgtDatastore = "TestSAN"
$tgtCluster = "GD SVRM"
$tgtPool = "Resources"
$vm = Get-VM -Name $vmName
$ds = Get-Datastore -Name $tgtDatastore
$esx = Get-Cluster -Name $tgtCluster | Get-VMHost | Get-Random
$rp = Get-ResourcePool -Name $tgtPool
$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = $ds.ExtensionData.MoRef
$spec.Host = $esx.ExtensionData.MoRef
$spec.Pool = $rp.ExtensionData.MoRef
$vm.ExtensionData.RelocateVM($spec,"defaultPriority")
Exception setting "Datastore": "Cannot convert the "System.Object[]" value of
type "System.Object[]" to type "VMware.Vim.ManagedObjectReference"."
At C:\movevm.ps1:12 char:1
+ $spec.Datastore = $ds.ExtensionData.MoRef
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [], SetValueInvocationExceptio
n
+ FullyQualifiedErrorId : ExceptionWhenSetting
Exception setting "Pool": "Cannot convert the "System.Object[]" value of type
"System.Object[]" to type "VMware.Vim.ManagedObjectReference"."
At C:\movevm.ps1:14 char:1
+ $spec.Pool = $rp.ExtensionData.MoRef
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [], SetValueInvocationExceptio
n
+ FullyQualifiedErrorId : ExceptionWhenSetting
Exception calling "RelocateVM" with "2" argument(s): "A specified parameter
was not correct: spec.location.datastore"
At C:\movevm.ps1:15 char:1
+ $vm.ExtensionData.RelocateVM($spec,"defaultPriority")
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [], MethodInvocationException
+ FullyQualifiedErrorId : VimException
I cant seem to get your code to work on any of my 3 hypervisors.
It looks as if you have multiple ResourcePool objects returned, hence the "System.Object[]" in the error message.
If you have multiple vSphere server connections open (check $global:defaultviservers), add a Server parameter on the Get-ResourcePool cmdlet.
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
I am having a hard time finding the information youre talking about. If i set the mode to single via Set-PowerCLIConfiguration -DefaultVIServerMode Single i still get errors in the script.....
Can you check if this line returns more than one object?
Get-Datastore -Name $tgtDatastore
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
PowerCLI C:\> Set-PowerCLIConfiguration -DefaultVIServerMode Single
Performing operation 'Update vSphere PowerCLI configuration.'?
[Y] Yes [A] Yes to All [N] No [L] No to All [S] Suspend [?] Help
(default is "Y"):y
Scope ProxyPolicy DefaultVIServerMode InvalidCertificateAction DisplayD
eprecati
onWarnin
gs
----- ----------- ------------------- ------------------------ --------
Session UseSystemProxy Multiple Unset True
User Multiple
AllUsers Single
PowerCLI C:\> Get-Datastore -Name "TestSAN"
Get-Datastore : 10/13/2016 12:19:36 PM Get-Datastore You are not
currently connected to any servers. Please connect first using a Connect
cmdlet.
At line:1 char:1
+ Get-Datastore -Name "TestSAN"
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : ResourceUnavailable: (:) [Get-Datastore], ViServ
erConnectionException
+ FullyQualifiedErrorId : Core_BaseCmdlet_NotConnectedError,VMware.VimAuto
mation.ViCore.Cmdlets.Commands.GetDatastore
PowerCLI C:\> Connect-VIServer -Server 10.40.30.242 -User "administrator@vsphere
.local" -Password "MYPASSHERE"
Name Port User
---- ---- ----
10.40.30.242 443 VSPHERE.LOCAL\Administrator
PowerCLI C:\> Get-Datastore -Name "TestSAN"
Name FreeSpaceGB CapacityGB
---- ----------- ----------
TestSAN 5,355.414 6,143.750
TestSAN 5,355.414 6,143.750
You seem to have two datastores with the same name, that is causing the error message.
You can select either one of those, or if you want it to be a specific one, you will have to use more parameters on the Get-Datastore cmdlet.
For example Location or RelatedObject.
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
The names of the data stores are identical between clusters for sure. I assume this means we cant have them named identically unless we specificy the related/location.
Looking at how to specify that. I am kinda lost. What would that look like for the other cluster?
You can do something like this
$clus1 = Get-Cluster -Name cluster1
$ds = Get-Datastore -Name ds1 -RelatedObject $clus1
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
LucD. This worked flawlessly.
Here is an example set of code.
$vmName = "NRFVORION1"
$tgtDatastore = "ISCSIOBRSERVER"
$tgtCluster = "GD SVRM"
$tgtPool = "Resources"
Set-PowerCLIConfiguration -DefaultVIServerMode single -Confirm:$false
Connect-VIServer -Server 10.40.30.242 -User "administrator@vsphere.local" -Password "mypwhere"
$clus1 = Get-Cluster -Name $tgtCluster
$vm = Get-VM -Name $vmName
$ds = Get-Datastore -Name $tgtDatastore -RelatedObject $clus1
$esx = Get-Cluster -Name $tgtCluster | Get-VMHost | Get-Random
$rp = Get-ResourcePool -Name $tgtPool -Location $tgtCluster
$spec = New-Object VMware.Vim.VirtualMachineRelocateSpec
$spec.Datastore = $ds.ExtensionData.MoRef
$spec.Host = $esx.ExtensionData.MoRef
$spec.Pool = $rp.ExtensionData.MoRef
$vm.ExtensionData.RelocateVM($spec,"defaultPriority")
Disconnect-VIServer -Server * -Force -Confirm:$false
One thing i noted was some devices do not move with say serial devices or printers hooked up.
I get error
Exception calling "RelocateVM" with "2" argument(s): "Currently connected
device 'Serial port 1' uses backing '/dev/char/serial/uart0', which is not
accessible."
At C:\sms\movevm.ps1:20 char:1
+ $vm.ExtensionData.RelocateVM($spec,"defaultPriority")
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [], MethodInvocationException
+ FullyQualifiedErrorId : VimException
There is a uart0 on the other server. I am trying to remove the port and readd it. If you have an example how to fix that. I would greatly appreciate your expert knowledge. 🙂
I did find some documentation on grammatically removing it. but it cannot do it with a powered on status.
Function Get-SerialPort {
Param (
[Parameter(Mandatory=$True,ValueFromPipeline=$True,ValueFromPipelinebyPropertyName=$True)]
$VM
)
Process {
Foreach ($VMachine in $VM) {
Foreach ($Device in $VMachine.ExtensionData.Config.Hardware.Device) {
If ($Device.gettype().Name -eq "VirtualSerialPort"){
$Details = New-Object PsObject
$Details | Add-Member Noteproperty VM -Value $VMachine
$Details | Add-Member Noteproperty Name -Value $Device.DeviceInfo.Label
If ($Device.Backing.FileName) { $Details | Add-Member Noteproperty Filename -Value $Device.Backing.FileName }
If ($Device.Backing.Datastore) { $Details | Add-Member Noteproperty Datastore -Value $Device.Backing.Datastore }
If ($Device.Backing.DeviceName) { $Details | Add-Member Noteproperty DeviceName -Value $Device.Backing.DeviceName }
$Details | Add-Member Noteproperty Connected -Value $Device.Connectable.Connected
$Details | Add-Member Noteproperty StartConnected -Value $Device.Connectable.StartConnected
$Details
}
}
}
}
}
Function Remove-SerialPort {
Param (
[Parameter(Mandatory=$True,ValueFromPipelinebyPropertyName=$True)]
$VM,
[Parameter(Mandatory=$True,ValueFromPipelinebyPropertyName=$True)]
$Name
)
Process {
$VMSpec = New-Object VMware.Vim.VirtualMachineConfigSpec
$VMSpec.deviceChange = New-Object VMware.Vim.VirtualDeviceConfigSpec
$VMSpec.deviceChange[0] = New-Object VMware.Vim.VirtualDeviceConfigSpec
$VMSpec.deviceChange[0].operation = "remove"
$Device = $VM.ExtensionData.Config.Hardware.Device | Foreach {
$_ | Where {$_.gettype().Name -eq "VirtualSerialPort"} | Where { $_.DeviceInfo.Label -eq $Name }
}
$VMSpec.deviceChange[0].device = $Device
$VM.ExtensionData.ReconfigVM_Task($VMSpec)
}
}
If i can remove the connected status i can migrate the vm and then edit it to be connected without issue.
Managed to get that to work with some more code from lucd.
$vmName = "TestVM"
$serialName = "Serial port 1"
$startConnected = $false
$connected = $false
$vm = Get-VM -Name TestVM
$spec = New-Object VMware.Vim.VirtualMachineConfigSpec
$dev = New-Object VMware.Vim.VirtualDeviceConfigSpec
$dev.Operation = "Edit"
$dev.Device = $vm.ExtensionData.Config.Hardware.Device |
where {$_ -is [VMware.Vim.VirtualSerialPort] -and $_.DeviceInfo.Label -eq $serialName}
$dev.Device.Connectable.Connected = $connected
$dev.Device.Connectable.StartConnected = $startConnected
$spec.DeviceChange += $dev
$vm.ExtensionData.ReconfigVM($spec
Thank you so much for all your help!