I am able to use Get-Host cmdlet to get total CPU capcity and the current cpu usage. However, I am not able to get the total reserved cpu. I also tried other cmdlet like Get-VMHostAdvancedConfiguration, but that doesn't include total reserved cpu info either. Any suggestion?
Ok, try this
foreach($esx in Get-VMHost){ $parent = Get-View $esx.ExtensionData.Parent
$rp = Get-View $parent.ResourcePool
Select -InputObject $esx -Property Name,
@{N="Total CPU Capacity MHz";E={$rp.Runtime.Cpu.MaxUsage}},
@{N="Reserved CPU Capacity MHz";E={$rp.Runtime.Cpu.ReservationUsed}},
@{N="Available CPU Capacity MHz";E={$rp.Runtime.Cpu.MaxUsage - $rp.Runtime.Cpu.ReservationUsed}} }
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Try this
Get-VMHost | Select Name, @{N="CPU Reservation MHz";E={$_.ExtensionData.SystemResources.Config.CpuAllocation.Reservation}}
The CPU, and other, resource values are available in the ResourceConfigSpec object.
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Thanks a lot, Luc. However, the value I got is even more than the total capacity on the host. Furthermore, I tried this on two hosts, they have identical hardware, but resources are reserved differently. They return the same value though. Did I miss anything?
No, that is the wrong one. That seems to be the total reservation for all VMs on the host.
This should be the host reservation you also see in the vSphere client
Get-VMHost | Select Name, @{N="CPU Reservation MHz";E={ $_.ExtensionData.SystemResources.Child | where {$_.Key -eq "host/system"} | %{ $_.Config.CpuAllocation.Reservation
} }}
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
Actually, I do mean that to get the cpu reserved for all VMs on the host, but it was showing the one I got from vSphere client.
PowerCLI C:\Program Files (x86)\VMware\Infrastructure\vSphere PowerCLI> Get-VMHost | Select Name, @{N="CPU Reservation MHz";E={$_.ExtensionData.SystemResources.Config.CpuAllocation.reservation}}Name CPU Reservation MHz---- -------------------10.10.15.227 6809610.10.15.228 68096
Ok, try this
foreach($esx in Get-VMHost){ $parent = Get-View $esx.ExtensionData.Parent
$rp = Get-View $parent.ResourcePool
Select -InputObject $esx -Property Name,
@{N="Total CPU Capacity MHz";E={$rp.Runtime.Cpu.MaxUsage}},
@{N="Reserved CPU Capacity MHz";E={$rp.Runtime.Cpu.ReservationUsed}},
@{N="Available CPU Capacity MHz";E={$rp.Runtime.Cpu.MaxUsage - $rp.Runtime.Cpu.ReservationUsed}} }
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
wow, it works! I really couldn't do this without your help. Thanks a ton!
Sorry, one more problem. It appears that your code works if there is only one host. If I get multiple hosts, it will return error:
Get-View : Cannot validate argument on parameter 'VIObject'. The argument is null or empty. Supply an argument that inot null or empty and then try the command again.
I couldn't figure out why.
Could it be that if fails against a host that is in a cluster ?
The script in it's current format will only work for stand-alone hosts.
But with the Foreach loop it shouldn't matter if it is run against multiple stand-alone hosts.
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
The multple hosts are managed by vCenter, but they are standalone, not in a cluster. This is how I connect to the hosts in my script.
Connect-VIServer 'host1' -User 'root' -Password 'password' -ErrorAction Continue -WarningAction ContinueConnect-VIServer 'host2' -User 'root' -Password 'password' -ErrorAction Continue -WarningAction Continue
Why do you do it like this ?
One Connect-VIserver to the vCenter should be enough.
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference
The reason I do so is because some hosts are not managed by the vCenter, and I only need to work on partial hosts from the vCenter. Is there any way I can modify the script so it can work for both standalone host and host managed by vCenter?
Are you connecting to all servers before you run the script ?
In that case the first Get-View will be executed against all open connections. The result is that $parent will be an array of objects instead of a single object.
And the next Get-View will give the error message you see because the Get-View cmdlet doesn't know how to handle that array of object in $parent.
The following variation is one way of handling this
$servers = "esx1","esx2"
foreach($server in $servers){ $srv = Connect-VIServer -Server $server -User root -Password '@password@'
$esx = Get-VMHost
$parent = Get-View $esx.ExtensionData.Parent
$rp = Get-View $parent.ResourcePool
Select -InputObject $esx -Property Name,
@{N="Total CPU Capacity MHz";E={$rp.Runtime.Cpu.MaxUsage}},
@{N="Reserved CPU Capacity MHz";E={$rp.Runtime.Cpu.ReservationUsed}},
@{N="Available CPU Capacity MHz";E={$rp.Runtime.Cpu.MaxUsage - $rp.Runtime.Cpu.ReservationUsed}} Disconnect-VIServer -Server $srv -Confirm:$false
}
Blog: lucd.info Twitter: @LucD22 Co-author PowerCLI Reference