VMware Cloud Community
Dorotej
Contributor
Contributor
Jump to solution

Setting VM overrides through PowerCLI

Hello,

I have a situation where I have to configure HA, monitoring, etc. for a specific set of VMs in a cluster. These VMs must have VM overrides configured differently compared to the rest of the cluster. I know how to perform it manually, but I have to re-create the same procedure in PowerCLI and I'm not exactly sure on how to apply the VM overrides to the VMs and not to the whole cluster.

For now i have written the following:

$vms = Get-VM -name <name>
ForEach ($vm in $vms){
  $spec = New-Object WMware.Vim.ClusterConfigSpecEx
  $spec.dasVmConfigSpec = New-Object VMware.Vim.ClusterDasVmConfigSpec[] (1)

  $spec.dasVmConfigSpec[0] = New-Object VMware.Vim.ClusterDasVmConfigSpec

  $spec.dasVmConfigSpec[0].operation = "add"

  $spec.dasVmConfigSpec[0].info = New-Object VMware.Vim.ClusterDasVmConfigInfo

  $spec.dasVmConfigSpec[0].info.key = New-Object VMware.Vim.ManagedObjectReference

  $spec.dasVmConfigSpec[0].info.key.type = "VirtualMachine"

  $spec.dasVmConfigSpec[0].info.key.value = $vm.ExtensionData.MoRef.Value
  $spec.dasVmConfigSpec[0].info.RestartPriority = "medium"

  $spec.dasVmConfigSpec[0].info.PowerOffOnIsolation = $True"

  $spec.dasVmConfigSpec[0].info.dasSettings = New-Object VMware.Vim.ClusterDasVmSettings

  $spec.dasVmConfigSpec[0].info.dasSettings.vmToolsMonitoringSettings = New-Object VMware.Vim.ClusterVmToolsMonitoringSettings

  $spec.dasVmConfigSpec[0].info.dasSettings.vmComponentProtectionSettings = New-Object VMware.Vim.ClusterVmComponentProtectionSettings


  ... Setting all the values for Component Protection and VM Monitorig ...


Now, near the end of the ForEach loop, I'm not sure on how to apply the created $spec configuration object to the $vm. Can it be done by something like this:

   $_this = Get-View -Id $vm.VMHost.Parent.Id

   $_this.ReconfigureComputeResource_Task($spec, $true)

And for ReconfigureComputeResource_Task, there are two parameters, but what does the 2nd parameter ($true) do?

If anyone could help, it would be much appreciated.

0 Kudos
1 Solution

Accepted Solutions
LucD
Leadership
Leadership
Jump to solution

That is one of the drawbacks of using Code Capture.

You really need to consult the API Reference to know what the captured code is actually doing/calling.

 

In this case the ReconfigureComputeResource method is called to make the changes you did in the Web Client.

 

From the description of the method you'll see that the 2nd parameter is the modify parameter.

From the description: "Flag to specify whether the specification ("spec") should be applied incrementally. If "modify" is false and the operation succeeds, then the configuration of the cluster matches the specification exactly; in this case any unset portions of the specification will result in unset or default portions of the configuration."

 

The $_.this notation is to indicate that the method is called on the object, a  cluster.

But in this case the vSphere object for a cluster.

This is not the same object as the .NET object for a cluster, which is returned by Get-Cluster.

 

There are 2 ways to go from the .NET object to the vSphere object.

  • via the ExtensionData property
  • via the Get-View cmdlet

 

One point to understand, the PowerCli framework offers 2 ways for all API methods.

One with the _Task suffix, where the call will return immediately and the task will run in the background.

The call without the _Task suffix, where the call will come back when the task is completed.

Something like the RunAsync switch on PowerCli cmdlets.

 

Your code would be something like this

$cluster = Get-Cluster -Name <name>
$vms = Get-VM -Name <name> -Location $cluster

ForEach ($vm in $vms){

  $spec = New-Object VMware.Vim.ClusterConfigSpecEx

  $spec.dasVmConfigSpec = New-Object VMware.Vim.ClusterDasVmConfigSpec[] (1)

  $spec.dasVmConfigSpec[0] = New-Object VMware.Vim.ClusterDasVmConfigSpec

  $spec.dasVmConfigSpec[0].operation = "add"

  $spec.dasVmConfigSpec[0].info = New-Object VMware.Vim.ClusterDasVmConfigInfo

  $spec.dasVmConfigSpec[0].info.key = New-Object VMware.Vim.ManagedObjectReference

  $spec.dasVmConfigSpec[0].info.key.type = "VirtualMachine"

  $spec.dasVmConfigSpec[0].info.key.value = $vm.ExtensionData.MoRef.Value

  $spec.dasVmConfigSpec[0].info.RestartPriority = "medium"

  $spec.dasVmConfigSpec[0].info.PowerOffOnIsolation = $True

  $spec.dasVmConfigSpec[0].info.dasSettings = New-Object VMware.Vim.ClusterDasVmSettings

  $spec.dasVmConfigSpec[0].info.dasSettings.vmToolsMonitoringSettings = New-Object VMware.Vim.ClusterVmToolsMonitoringSettings

  $spec.dasVmConfigSpec[0].info.dasSettings.vmComponentProtectionSettings = New-Object VMware.Vim.ClusterVmComponentProtectionSettings

}

$cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true)


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

View solution in original post

6 Replies
LucD
Leadership
Leadership
Jump to solution

That is one of the drawbacks of using Code Capture.

You really need to consult the API Reference to know what the captured code is actually doing/calling.

 

In this case the ReconfigureComputeResource method is called to make the changes you did in the Web Client.

 

From the description of the method you'll see that the 2nd parameter is the modify parameter.

From the description: "Flag to specify whether the specification ("spec") should be applied incrementally. If "modify" is false and the operation succeeds, then the configuration of the cluster matches the specification exactly; in this case any unset portions of the specification will result in unset or default portions of the configuration."

 

The $_.this notation is to indicate that the method is called on the object, a  cluster.

But in this case the vSphere object for a cluster.

This is not the same object as the .NET object for a cluster, which is returned by Get-Cluster.

 

There are 2 ways to go from the .NET object to the vSphere object.

  • via the ExtensionData property
  • via the Get-View cmdlet

 

One point to understand, the PowerCli framework offers 2 ways for all API methods.

One with the _Task suffix, where the call will return immediately and the task will run in the background.

The call without the _Task suffix, where the call will come back when the task is completed.

Something like the RunAsync switch on PowerCli cmdlets.

 

Your code would be something like this

$cluster = Get-Cluster -Name <name>
$vms = Get-VM -Name <name> -Location $cluster

ForEach ($vm in $vms){

  $spec = New-Object VMware.Vim.ClusterConfigSpecEx

  $spec.dasVmConfigSpec = New-Object VMware.Vim.ClusterDasVmConfigSpec[] (1)

  $spec.dasVmConfigSpec[0] = New-Object VMware.Vim.ClusterDasVmConfigSpec

  $spec.dasVmConfigSpec[0].operation = "add"

  $spec.dasVmConfigSpec[0].info = New-Object VMware.Vim.ClusterDasVmConfigInfo

  $spec.dasVmConfigSpec[0].info.key = New-Object VMware.Vim.ManagedObjectReference

  $spec.dasVmConfigSpec[0].info.key.type = "VirtualMachine"

  $spec.dasVmConfigSpec[0].info.key.value = $vm.ExtensionData.MoRef.Value

  $spec.dasVmConfigSpec[0].info.RestartPriority = "medium"

  $spec.dasVmConfigSpec[0].info.PowerOffOnIsolation = $True

  $spec.dasVmConfigSpec[0].info.dasSettings = New-Object VMware.Vim.ClusterDasVmSettings

  $spec.dasVmConfigSpec[0].info.dasSettings.vmToolsMonitoringSettings = New-Object VMware.Vim.ClusterVmToolsMonitoringSettings

  $spec.dasVmConfigSpec[0].info.dasSettings.vmComponentProtectionSettings = New-Object VMware.Vim.ClusterVmComponentProtectionSettings

}

$cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true)


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

Dorotej
Contributor
Contributor
Jump to solution

Hello,

Thanks for the quick and in-depth respnose. Not actually using Code Capture as we don't have it, this code was written the old-fashioned way, but I'm fairly new to PowerCLI scripting and I couldn't find much on configuring individual VMs on the cluster. I guess I've missed the API reference to ReconfigureComputeResource method in the documentation, probably entered something wrong in the search.

So what I'm guetting from the desciption of the modify parameter, if $false is used, it will set the configuration of the whole cluster to the created $spec object?

0 Kudos
LucD
Leadership
Leadership
Jump to solution

That is correct.

Note that this will set defaults for all the cluster parameters you didn't include in the $spec.

Also, some properties in $spec are obligatory, in other words, they need to be present and set.

These properties are not marked with a red asterisk in the parameter description.


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

0 Kudos
teddo1
Contributor
Contributor
Jump to solution

Hi Luc. Do you know if there's an easy way to simply export a list of VMs from vCenter that have a DRS override enabled? Unfortunately the usual export list function built-in to vCenter doesn't seem to be available in the VM Overrides view. RVTools doesn't seem to collect this information either.

0 Kudos
LucD
Leadership
Leadership
Jump to solution

Something like this?

Get-Cluster -PipelineVariable cluster |
ForEach-Object -Process {
  $cluster.ExtensionData.Configuration.DrsVmConfig |
  ForEach-Object -Process {
    New-Object -TypeName PSObject -Property ([ordered]@{
      Cluster = $cluster.Name
      VM = (Get-View -Id $_.Key -Property Name).Name
      Automation = $_.Behavior
    })
  }
}


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

teddo1
Contributor
Contributor
Jump to solution

This worked perfectly, thank you! You're the best 🙂

0 Kudos