Using DRS rules

To control the placement of virtual machines on hosts in a cluster, you can use DRS affinity rules or anti-affinity rules. There are two types of affinity rules:

  • VM-VM affinity rules: These rules specify affinity or anti-affinity between virtual machines. An affinity rule specifies that DRS should or must keep a group of virtual machines together on the same host. A use case of the affinity rules can be performance because virtual machines on the same hosts have the fastest network connection possible. An anti-affinity rule specifies that DRS should or must keep a group of virtual machines on separate hosts. This prevents you from losing all of the virtual machines in the group if a host crashes.
  • VM-Host affinity rules: These rules specify affinity or anti-affinity between a group of virtual machines and a group of hosts. An affinity rule specifies that the group of virtual machines should or must run on the group of hosts. An anti-affinity rule specifies that the group of virtual machines should or must not run on the group of hosts.

In PowerCLI, there are cmdlets to use VM-VM affinity rules. To use VM-Host affinity rules, you have to, unfortunately, use the vSphere API.

Creating VM-VM DRS rules

To create a VM-VM DRS rule, you can use the New-DrsRule cmdlet that has the following syntax:

New-DrsRule [-Name] <String> [-Cluster] <Cluster[]> [-Enabled
    [<Boolean>]] -KeepTogether [<Boolean>] -VM <VirtualMachine[]>
    [-RunAsync] [-Server <VIServer[]>] [-WhatIf] [-Confirm] 
    [<CommonParameters>]

The -Name, -Cluster, -KeepTogether, and -VM parameters are required.

If the value of the -KeepTogether parameter is $true, the new DRS rule is an affinity rule. If the value is $false, the new DRS rule is an anti-affinity rule.

If the value of -Enabled parameter is $true, the new DRS rule is enabled. If the value is $false, it is disabled.

In the following example, you will create a new, enabled DRS VM-VM affinity rule named Keep VM1 and VM2 together for Cluster01. The DRS rule will keep the two virtual machines VM1 and VM2 together on the same host:

PowerCLI C:> New-DrsRule -Name 'Keep VM1 and VM2 together'
    -Cluster Cluster01 -VM VM1,VM2 -KeepTogether:$true -Enabled:$true


    Name                      Enabled Type       VMIDs
----                      ------- ----       -----
Keep VM1 and VM2 together True    VMAffinity {VirtualMachine-vm-125, 
                                                  VirtualMachine-vm-105}

In the following screenshot of the vSphere Web Client, you will see the window of the vSphere Web Client, which you can use to create a DRS rule filled with the same settings as in the preceding PowerCLI command:

Creating VM-VM DRS rules

In the second example, you will create a new DRS VM-VM anti-affinity rule named Separate VM3 and VM4 for Cluster01:

PowerCLI C:> New-DrsRule -Name 'Separate VM3 and VM4'
    -Cluster Cluster01 -VM VM3,VM4 -KeepTogether:$false -Enabled:$true


    Name                 Enabled Type           VMIDs
----                 ------- ----           -----
Separate VM3 and VM4 True    VMAntiAffinity {VirtualMachine-vm-107,
                                                 VirtualMachine-vm-126}

Creating VM-host DRS rules

Unfortunately, there are no PowerCLI cmdlets to create a VM-Host affinity rule. You have to use the vSphere API to do this. There are three steps involved in creating a VM-Host affinity rule:

  1. Creating a virtual machines DRS group.
  2. Creating a host's DRS group.
  3. Creating a virtual machines to hosts DRS rule.

Creating virtual machines DRS groups

While creating a virtual machines DRS group, you have to add at least one virtual machine to this group. In the following example, you will create a virtual machines DRS group named Cluster01 VMs should run on host 192.168.0.133 for Cluster01 and add virtual machine VM1 to this DRS group.

First, you create a ClusterConfigSpecEx object. Then, you add an array containing one ClusterGroupSpec object to the GroupSpec property of the ClusterConfigSpecEx object. The operation property of the ClusterGroupSpec object is given the value add. A ClusterVmGroup object is assigned to the info property of the ClusterGroupSpec object. The name of the DRS group is assigned to the name property of the ClusterVmGroup object. The MoRef of the virtual machine that will be added to the DRS group is assigned to the vm property of the ClusterVmGroup object. Finally, the cluster's ReconfigureComputeResource_Task() method is called to reconfigure the cluster and to add the DRS group:

# Creating a Virtual Machines DRS Group 
$Cluster = Get-Cluster -Name Cluster01 
$VM = Get-VM -Name VM1 -Location $Cluster 
$DRSGroupName = 'Cluster01 VMs should run on host 192.168.0.133' 
$spec = New-Object VMware.Vim.ClusterConfigSpecEx 
$spec.groupSpec = New-Object VMware.Vim.ClusterGroupSpec[] (1) 
$spec.groupSpec[0] = New-Object VMware.Vim.ClusterGroupSpec 
$spec.groupSpec[0].operation = 'add' 
$spec.groupSpec[0].info = New-Object VMware.Vim.ClusterVmGroup 
$spec.groupSpec[0].info.name = $DRSGroupName 
$spec.groupSpec[0].info.vm += $VM.ExtensionData.MoRef 
$Cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true) 

Creating hosts DRS groups

Creating a hosts DRS group is similar to creating a virtual machine DRS group. Instead of adding a ClusterVmGroup object to the info property of the ClusterGroupSpec object, you have to add a ClusterHostGroup object. The host property of the ClusterHostGroup will get the MoRef of the host you want to add to the DRS group assigned. You have to add at least one host to a hosts DRS group.

In the following example, you will create a hosts DRS group named Cluster01 192.168.0.133 Hosts DRS Group, and you will add the host 192.168.0.133 to this group:

# Creating a Hosts DRS Group 
$Cluster = Get-Cluster -Name Cluster01 
$VMHost = Get-VMHost -Name 192.168.0.133 -Location $Cluster 
$DRSGroupName = 'Cluster01 192.168.0.133 Hosts DRS Group' 
$spec = New-Object VMware.Vim.ClusterConfigSpecEx 
$spec.groupSpec = New-Object VMware.Vim.ClusterGroupSpec[] (1) 
$spec.groupSpec[0] = New-Object VMware.Vim.ClusterGroupSpec 
$spec.groupSpec[0].operation = "add" 
$spec.groupSpec[0].info = New-Object VMware.Vim.ClusterHostGroup 
$spec.groupSpec[0].info.name = $DRSGroupName 
$spec.groupSpec[0].info.host += $VMHost.ExtensionData.MoRef 
$Cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true) 

Retrieving DRS groups

There are no cmdlets to retrieve DRS groups. You will have to use the vSphere API. The DRS groups are in the ConfigurationEx.Group property of a vSphere ClusterComputeResource object.

The following example will show you how to retrieve the DRS groups of Cluster01:

PowerCLI C:> (Get-Cluster -Name Cluster01).ExtensionData
    .ConfigurationEx.Group


    Vm          : {VirtualMachine-vm-125}
LinkedView  :
Name        : Cluster01 VMs should run on host 192.168.0.133
UserCreated :
UniqueID    :
Host        : {HostSystem-host-109}
LinkedView  :
Name        : Cluster01 192.168.0.133 Hosts DRS Group
UserCreated :
UniqueID    :

Modifying DRS groups

If you want to modify a DRS group, the only thing you can do is add or remove virtual machines or hosts to or from the DRS group. There are no PowerCLI cmdlets to do this, so you have to use the vSphere API.

Adding virtual machines to a DRS group

In the first example, you will add virtual machines VM2, VM4, and VM7 to the DRS group Cluster01 VMs should run on host 192.168.0.133. Because the structure of ClusterConfigSpecEx objects is always the same, I will explain only what is unique in this example. In this case, the operation is edit. The DRS group is assigned to the info property. All of the new group members are added to the info.vm property:

# Adding virtual machines to a DRS group 
$Cluster = Get-Cluster -Name Cluster01 
$GroupName = "Cluster01 VMs should run on host 192.168.0.133" 
$VMs = Get-VM -Name VM2,VM4,VM7 
$spec = New-Object VMware.Vim.ClusterConfigSpecEx 
$spec.groupSpec = New-Object VMware.Vim.ClusterGroupSpec[] (1) 
$spec.groupSpec[0] = New-Object VMware.Vim.ClusterGroupSpec 
$spec.groupSpec[0].operation = "edit" 
$spec.groupSpec[0].info = $Cluster.ExtensionData.ConfigurationEx.Group | 
  Where-Object {$_.Name -eq $GroupName}  
foreach ($VM in $VMs) 
{ 
  $spec.groupSpec[0].info.vm += $VM.ExtensionData.MoRef 
} 
$Cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true) 

Removing virtual machines from a DRS group

In the second example about modifying DRS groups, the virtual machines VM4 and VM7 will be removed from the DRS group Cluster01 VMs should run on host 192.168.0.133.

This example looks a lot like the preceding one. The difference is that virtual machines are removed from the info.vm property using the Where-Object cmdlet and the -notcontains operator. Only the virtual machines that are not in the list of virtual machines to be removed are assigned to the info.vm property:

# Removing virtual machines from a DRS group 
$Cluster = Get-Cluster -Name Cluster01 
$GroupName = "Cluster01 VMs should run on host 192.168.0.133" 
$VMs = Get-VM -Name VM4,VM7 
$VMsMorefs = $VMs | ForEach-Object {$_.ExtensionData.MoRef} 
$spec = New-Object VMware.Vim.ClusterConfigSpecEx 
$spec.groupSpec = New-Object VMware.Vim.ClusterGroupSpec[] (1) 
$spec.groupSpec[0] = New-Object VMware.Vim.ClusterGroupSpec 
$spec.groupSpec[0].operation = "edit" 
$spec.groupSpec[0].info = New-Object VMware.Vim.ClusterVmGroup 
$spec.groupSpec[0].info.name = $GroupName 
$spec.groupSpec[0].info.vm = $Cluster.ExtensionData.ConfigurationEx.Group | 
  Where-Object {$_.Name -eq $GroupName} | 
  Select-Object -ExpandProperty vm | 
  Where-Object {$VMsMorefs -notcontains $_} 
$Cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true) 

Note

Remember that you cannot remove all of the virtual machines or hosts from a DRS group. A DRS group needs at least one group member.

Adding hosts to a DRS group and removing hosts from a DRS group is similar to adding virtual machines to a DRS group or removing virtual machines from a DRS group. I leave this to you as an exercise to solve (Hint: use Get-VMHost instead of Get-VM).

Tip

More information about the VMware.VIM.* objects used in the preceding examples can be found in VMware vSphere API Reference Documentation: http://pubs.vmware.com/vsphere-65/index.jsp#com.vmware.wssdk.apiref.doc/right-pane.html .

Removing DRS groups

Removing DRS groups is similar to preceding DRS groups operations. To remove a DRS group, the operation is remove, and the removeKey is the DRS group's name.

The following example will remove the DRS group Cluster01 VMs should run on host 192.168.0.133:

# Removing a DRS group 
$Cluster = Get-Cluster -Name Cluster01 
$GroupName = "Cluster01 VMs should run on host 192.168.0.133" 
$spec = New-Object VMware.Vim.ClusterConfigSpecEx 
$spec.groupSpec = New-Object VMware.Vim.ClusterGroupSpec[] (1) 
$spec.groupSpec[0] = New-Object VMware.Vim.ClusterGroupSpec 
$spec.groupSpec[0].operation = "remove" 
$spec.groupSpec[0].removeKey = $GroupName 
$Cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true) 

Creating Virtual Machines to Hosts DRS rules

Finally, you have to relate the virtual machines DRS group to the hosts DRS group in a virtual machines to hosts DRS rule. There are four possible relations:

  • Must run on hosts in group
  • Should run on hosts in group
  • Must not run on hosts in group
  • Should not run on hosts in group

In the example given, you will create a Should run on hosts in group virtual machines to hosts DRS rule to give preference to virtual machine VM1 to run on host 192.168.0.133.

First, a ClusterConfigSpecEx object is created. An array of one ClusterRuleSpec object is assigned to the rulesSpec property of the ClusterConfigSpecEx object. The operation property of rulesSpec is set to add. A ClusterVmHostRuleInfo object is assigned to the info property of rulesSpec. The enabled property of the ClusterVmHostRuleInfo object is set to $true. The name property is given the name of the DRS rule. Because it is a Should run on hosts in group DRS rule, the mandatory property is set to $false. The userCreated property is set to $true. The vmGroupName and affineHostGroupName properties are assigned the names of the related DRS groups. Finally, the cluster's ReconfigureComputeResource_Task() method is called to create the DRS rule:

# Creating a Virtual Machines to Hosts DRS rule 
$Cluster = Get-Cluster -Name Cluster01 
$spec = New-Object VMware.Vim.ClusterConfigSpecEx 
$spec.rulesSpec = New-Object VMware.Vim.ClusterRuleSpec[] (1) 
$spec.rulesSpec[0] = New-Object VMware.Vim.ClusterRuleSpec 
$spec.rulesSpec[0].operation = "add" 
$spec.rulesSpec[0].info = New-Object VMware.Vim.ClusterVmHostRuleInfo 
$spec.rulesSpec[0].info.enabled = $true 
$spec.rulesSpec[0].info.name = "Cluster01 VM1 should run on host 192.168.0.133 DRS Rule" 
$spec.rulesSpec[0].info.mandatory = $false 
$spec.rulesSpec[0].info.userCreated = $true 
$spec.rulesSpec[0].info.vmGroupName = "Cluster01 VMs should run on host 192.168.0.133" 
$spec.rulesSpec[0].info.affineHostGroupName = "Cluster01 192.168.0.133 Hosts DRS Group" 
$Cluster.ExtensionData.ReconfigureComputeResource_Task($spec, $true) 

If you want to create a Must run on hosts in group DRS rule, you only have to change the line $spec.rulesSpec[0].info.mandatory = $false in the preceding code to the following:

$spec.rulesSpec[0].info.mandatory = $true 

If you want to create a Must not run on hosts in group or Should not run on hosts in group DRS group, you have to assign the DRS hosts group name to $spec.rulesSpec[0].info.antiAffineHostGroupName instead of $spec.rulesSpec[0].info.affineHostGroupName.

In the following screenshot of the vSphere Web Client, you will see the virtual machines to hosts DRS rule Cluster01 VM1 should run on host 192.168.0.133 DRS Rule created with the preceding PowerCLI commands:

Creating Virtual Machines to Hosts DRS rules

Retrieving DRS Rules

You can use the Get-DrsRule cmdlet to retrieve the DRS rules of the specified clusters. The syntax of this cmdlet is as follows. The first parameter set is the default:

Get-DrsRule [[-Name] <String[]>] [-Cluster] <Cluster[]>
    [[-VM] <VirtualMachine[]>] [-Type <ResourceSchedulingRuleType[]>]
    [-Server <VIServer[]>] [<CommonParameters>]

The second parameter set is to retrieve DRS rules that reference the specified ESXi hosts:

Get-DrsRule [[-Name] <String[]>] [-Cluster] <Cluster[]> [[-VM]
    <VirtualMachine[]>] [-VMHost <VMHost[]>] [-Server <VIServer[]>]
    [<CommonParameters>]

The -Cluster parameter is required. You cannot use the -Type and -VMHost parameters in the same command because they are in different parameter sets.

If you don't specify the -Type or -VMHost parameters, you will only retrieve VM-VM affinity or VM-VM anti-affinity rules, as in the following example:

PowerCLI C:> Get-DrsRule -Cluster Cluster01


    Name                              Enabled Type           VMIDs
----                              ------- ----           -----
Keep VM1 and VM2 together         True    VMAffinity     {VirtualM...
Separate VM3 and VM4              True    VMAntiAffinity {VirtualM...

If you also want to retrieve VM-Host DRS rules, you have to specify all of the possible types as the value of the -Type parameter, as we will do in the following example:

PowerCLI C:> Get-DrsRule -Cluster Cluster01
    -Type VMAffinity,VMAntiAffinity,VMHostAffinity


    Name                              Enabled Type           VMIDs
----                              ------- ----           -----
Keep VM1 and VM2 together         True    VMAffinity     {VirtualM...
Separate VM3 and VM4              True    VMAntiAffinity {VirtualM...
Cluster01 VM1 should run on ho... True    VMHostAffinity {VirtualM...

You can also retrieve all the DRS rules that involve certain virtual machines using the -VM parameter:

PowerCLI C:> Get-DrsRule -Cluster Cluster01 -VM VM2


    Name                              Enabled Type           VMIDs
----                              ------- ----           -----
Keep VM1 and VM2 together         True    VMAffinity     {VirtualM...

To retrieve all of the DRS rules that involve specific hosts, use the -VMHost parameter using the following command:

PowerCLI C:> Get-DrsRule -Cluster Cluster01 -VMHost 192.168.0.133


    Name                              Enabled Type           VMIDs
----                              ------- ----           -----
Cluster01 VM1 should run on ho... True    VMHostAffinity {VirtualM...

Modifying DRS rules

To modify a DRS rule, you can use the Set-DrsRule cmdlet. The syntax of this cmdlet is as follows:

Set-DrsRule [[-Enabled] [<Boolean>]] [-Rule] <DrsRule[]>
    [-Name <String>] [-VM <VirtualMachine[]>] [-RunAsync] [-Server
    <VIServer[]>] [-WhatIf] [-Confirm] [<CommonParameters>]

The -Rule parameter is required.

In the following example, the DRS rule Keep VM1 and VM2 together of Cluster01 will be disabled:

PowerCLI C:> Get-DrsRule -Name 'Keep VM1 and VM2 together'
    -Cluster Cluster01 | Set-DrsRule -Enabled:$false


    Name                              Enabled Type           VMIDs
----                              ------- ----           -----
Keep VM1 and VM2 together         False   VMAffinity     {VirtualM...

Removing DRS rules

The Remove-DrsRule cmdlet can be used to remove a DRS rule. The syntax of the Remove-DrsRule cmdlet is as follows:

Remove-DrsRule [-Rule] <DrsRule[]> [-RunAsync] [-WhatIf]
    [-Confirm] [<CommonParameters>]

The -Rule parameter is required.

In the following example, the Keep VM1 and VM2 together of Cluster01 is removed:

PowerCLI C:> Get-DrsRule -Cluster Cluster01 -Name 'Keep VM1
    and VM2 together' | Remove-DrsRule -Confirm:$false

The preceding command does not return any output.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
13.58.252.8