scottg69
Contributor
Contributor

Host and VM Count

Jump to solution

Folks I am pretty new to this powershell stuff and have a little problem, how can I display a 0 when I have no VMs powered off or hosts in an unconnected state when running the following code:

Get-Cluster | %{$Cluster = $_;

$OnVM = Get-VM -Location $Cluster | where-object { $_.powerstate -eq "poweredon"} | measure-object;

$OffVM = Get-VM -Location $Cluster | where-object { $_.powerstate -eq "poweredoff"} | measure-object;

$OnHost = Get-VMHost -Location $Cluster | where-object { $_.state -eq "connected"} | measure-object;

$OffHost = Get-VMHost -Location $Cluster | where-object { $_.state -ne "connected"} | measure-object;

Write-host $Cluster.Name

Write-Host "VMs On = " $OnVM.Count

Write-Host "VMs Off = " $OffVm.Count

Write-Host "Hosts Connected = " $OnHost.Count

Write-Host "Hosts Not Connected = " $OffHost.Count

}

I have tried all sorts of if statments but cant seem to get a 0 when there is no count data.

Thanks in advance.

S

0 Kudos
1 Solution

Accepted Solutions
ggochkov
VMware Employee
VMware Employee

my mistake - the last line I meant:

Write-Host "Hosts Not Connected = " $OffHostCount

View solution in original post

0 Kudos
8 Replies
ggochkov
VMware Employee
VMware Employee

In fact when there is no result for the $OffHost or $OffVM their value is $null and the values Write-Host "Hosts Not Connected = " $OffHost.Count

the same as for VMs

0 Kudos
ggochkov
VMware Employee
VMware Employee

my mistake - the last line I meant:

Write-Host "Hosts Not Connected = " $OffHostCount

0 Kudos
LucD
Leadership
Leadership

Not too elegant but this should do the trick

Get-Cluster | %{$Cluster = $_;

$OnVM = Get-VM -Location $Cluster | where-object { $_.powerstate -eq "poweredon"} | measure-object;
$OffVM = Get-VM -Location $Cluster | where-object { $_.powerstate -eq "poweredoff"} | measure-object;
$OnHost = Get-VMHost -Location $Cluster | where-object { $_.state -eq "connected"} | measure-object;
$OffHost = Get-VMHost -Location $Cluster | where-object { $_.state -ne "connected"} | measure-object;
Write-host $Cluster.Name

Write-Host "VMs On = " (&{if($OnVM -eq $null){0} else{$OnVM.Count}})
Write-Host "VMs Off = " (&{if($OffVM -eq $null){0} else{$OffVM.Count}})
Write-Host "Hosts Connected = " (&{if($OnHost -eq $null){0} else{$OnHost.Count}})
Write-Host "Hosts Not Connected = " (&{if($OffHost -eq $null){0} else{$OffHost.Count}})
}


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

0 Kudos
scottg69
Contributor
Contributor

Folks, both answers do the trick nicely. Thanks for the prompt response.

S

0 Kudos
hugopeeters
Hot Shot
Hot Shot

This is how I would do it:

ForEach ($cluster in Get-Cluster)
{
Write-Host "==========="
Write-Host $Cluster.Name
Write-Host "==========="
$VMs = Get-VM -Location $Cluster
$Hosts = Get-VMHOst -Location $Cluster
$VMs | Group-Object PowerState | Format-Table @{L="Virtual Machines";E={$_.Name}}, Count -AutoSize
$Hosts | Group-Object State | Format-Table @{L="Hosts";E={$_.Name}}, Count -AutoSize
}

You won't get a line for PoweredOff vm's if there are none.

Another way to do it: ONELINER!

Get-Cluster | Select Name, @{N="VMs ON";E={(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOn"} | Measure-Object).Count}}, @{N="VMs OFF";E={(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOff"} | Measure-Object).Count}}, @{N="Hosts Connected";E={(Get-VMHost | ?{$_.State -eq "Connected"} | Measure-Object).Count}}, @{N="Hosts Disconnected";E={(Get-VMHost | ?{$_.State -ne "Connected"} | Measure-Object).Count}}

Still no zeros displayed...

0 Kudos
hugopeeters
Hot Shot
Hot Shot

Combining my oneliner with LucD's thick to display zeros:

Get-Cluster | Select Name, @{N="VMs ON";E={If(!(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOn"})){0}Else{(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOn"} | Measure-Object).Count}}}, @{N="VMs OFF";E={If(!(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOff"})){0}Else{(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOff"} | Measure-Object).Count}}}, @{N="Hosts Connected";E={If(!(Get-VMHost | ?{$_.State -eq "Connected"})){0}Else{(Get-VMHost | ?{$_.State -eq "Connected"} | Measure-Object).Count}}}, @{N="Hosts Disconnected";E={If(!(Get-VMHost | ?{$_.State -ne "Connected"})){0}Else{(Get-VMHost | ?{$_.State -ne "Connected"} | Measure-Object).Count}}}

With line continuation characters for readability:

Get-Cluster | Select Name, `
@{N="VMs ON";E={If(!(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOn"})){0}Else{(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOn"} | Measure-Object).Count}}}, `
@{N="VMs OFF";E={If(!(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOff"})){0}Else{(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOff"} | Measure-Object).Count}}}, `
@{N="Hosts Connected";E={If(!(Get-VMHost | ?{$_.State -eq "Connected"})){0}Else{(Get-VMHost | ?{$_.State -eq "Connected"} | Measure-Object).Count}}}, `
@{N="Hosts Disconnected";E={If(!(Get-VMHost | ?{$_.State -ne "Connected"})){0}Else{(Get-VMHost | ?{$_.State -ne "Connected"} | Measure-Object).Count}}}

0 Kudos
LucD
Leadership
Leadership

Continuing on the theme.... Smiley Wink

Seen the performance cost of the Get-VM cmdlet the following should be a bit faster

Get-Cluster | Select Name, `
@{N="VMs ON";E={$s=(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOn"});if(!$s){0}else{($s | Measure-Object).Count}}}, `
@{N="VMs OFF";E={$s=(Get-VM -Location $_ | ?{$_.PowerState -eq "PoweredOff"});if(!$s){0}else{($s | Measure-Object).Count}}}, `
@{N="Hosts Connected";E={$s=(Get-VMHost | ?{$_.State -eq "Connected"});if(!$s){0}else{($s | Measure-Object).Count}}}, `
@{N="Hosts Disconnected";E={$s=(Get-VMHost | ?{$_.State -ne "Connected"});if(!$s){0}else{($s | Measure-Object).Count}}}


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

0 Kudos
scottg69
Contributor
Contributor

Thanks LucD, will give that a go in a bit. I have one other question, I am trying to use a function to control my code but I having an issues with a custom object I using to store the returns, every time the function exits the object is deleted. The object I am tlaking about is $VMHostCount in the following code:

Function GetVMHostNums {

Write-Host "I am working - " $Cluster.Name

$OnVM = Get-VM -Location $Cluster | where-object { $_.powerstate -eq "poweredon"} | measure-object;

$OffVM = Get-VM -Location $Cluster | where-object { $_.powerstate -eq "poweredoff"} | measure-object;

$OnHost = Get-VMHost -Location $Cluster | where-object { $_.state -eq "connected"} | measure-object;

$OffHost = Get-VMHost -Location $Cluster | where-object { $_.state -ne "connected"} | measure-object;

$row = "" | select Cluster, VMsOn, VMsOff, HostsOn, HostsOff, TimeStamp

$row.Cluster = $Cluster.Name

$row.VmsOn = (&{if($OnVM.Count -eq $null){0} else{$OnVM.Count}})

$row.VMsOff = (&{if($OffVM.Count -eq $null){0} else{$OffVM.Count}})

$row.HostsOn = (&{if($OnHost.Count -eq $null){0} else{$OnHost.Count}})

$row.HostsOff = (&{if($OffHost.Count -eq $null){0} else{$OffHost.Count}})

$row.Timestamp = $startDate

Write-Host $row

$VMHostCount += $row;

}

                                                                                                                                1. Main Calling Code ################################################################

Add-PSsnapin VMware.VimAutomation.Core

Initialize-VIToolkitEnvironment.ps1

Connect-VIServer ???????? -User ?????????? -Password ????????

$startDate = (get-date).adddays(-1).tostring("dd/MM/yyyy")

$finishDate = (get-date).adddays(-0).tostring("dd/MM/yyyy")

$VMHostCount = @()

Get-Cluster | %{$Cluster = $_;

Write-Host $Cluster.Name;

GetVMHostNums

}

Would apprecaite any help you could give with this, as I say I am pretty new to powershell but could do this in VBS ok.

Thanks

S

0 Kudos