Power to the API (Complete control over VMware using Powershell!)


    The power of the API


    Have you been playing around with the VMware cmdlets for Windows Powershell from the VI Toolkit (beta) yet? I’ll you like the cmdlets that are offered, but you also wish there was more. I’m sure you have thought at some point in time: “I sure wish I could … with this toolkit.” I know I have.

    That’s why I have been searching for ways to do more with the VI Toolkit. And I have found the holy grail in the following post from Carter Shanklin, product manager at VMware:



    He explains that the VI Toolkit has a layered structure; some common commands are available as ready-to-use cmdlets, but the full power of the Virtual Infrastructure API can be unleashed by some more advanced scripting!



    I personally think the helpfiles and online information leave much to be desired, so I have decided to try and explain to you how this stuff works.


    Find-EntityViews, Find-EntityView


    There are six types of managed entities within the Virtual Infrastructure:

  1. ComputeResource
  2. Datacenter
  3. Folder
  4. HostSystem
  5. ResourcePool
  6. VirtualMachine

    Objects representing these entities and their extensive properties can be retrieved using the command Find-Entityviews:

    PS P:>$VMHosts = Find-EntityViews -ViewType HostSystem

    The $VMHosts variable will now hold a collection of HostSystem objects:

    PS P:> $VMHosts.gettype()

    IsPublic IsSerial Name                                     BaseType

    ——– ——– —-                                     ——–

    True     True     Object[]                                 System.Array


    PS P:> $VMHosts[0].gettype()

    IsPublic IsSerial Name                                     BaseType

    ——– ——– —-                                     ——–

    True     False    HostSystem                               VMware.Vim.ManagedEntity

    The objects have a lot of useful properties, so start exploring them. You can go deeper and deeper into the tree of properties by adding a dot and the property name behind the variable:

    PS P:> $vmhosts[0].config.product

    Name            : VMware ESX Server

    FullName        : VMware ESX Server 3.5.0 build-82663

    Vendor          : VMware, Inc.

    Version         : 3.5.0

    Build           : 82663

    LocaleVersion   : INTL

    LocaleBuild     : 000

    OsType          : vmnix-x86

    ProductLineId   : esx

    ApiType         : HostAgent

    ApiVersion      : 2.5.0

    DynamicType     :

    DynamicProperty :


    Ok, cool. But what does Find-EntityView do?

    It’s a strange cmdlet, the one without the “s”. It does the same thing as Find-EntityViews, but only returns the first object in the array. I can’t really think of any advantages of using this cmdlet, besides potentially increased performance. But I think you risk missing important information. If you are looking for information about one specific ESX Host, you can use the -Filter parameter with Find-EntityViews too.



    Using the -Filter parameter with Find EntityView(s) is not as simple as it might seem. When simply trying to specify a filter, you’ll run into the following error:

    PS P:>Find-EntityViews -ViewType HostSystem -Filter E*

    Find-EntityViews : Cannot bind parameter ‘Filter’. Cannot convert value “E*” to type “System.Collections.Specialized.NameValueCol

    lection”. Error: “Invalid cast from ‘System.String’ to ‘System.Collections.Specialized.NameValueCollection’.”

    At line:1 char:46

    + Find-EntityViews -ViewType HostSystem -Filter  <<<< E*

    Apparently, the filter cannot be a simple string. It should be an object of type ‘System.Collections.Specialized.NameValueCollection’. Okay, no problem. Let’s make one:

    PS P:>$nvc = New-Object -TypeName System.Collections.Specialized.NameValueCollection

    Next, we add a name-value pair representing the property and value we would like to filter on:

    PS P:>$nvc.add(“Name”,”esxserver001″)

    Finally, we can run the Find-EntityViews command again using our filter:

    PS P:>Find-EntityViews -ViewType HostSystem -Filter $nvc

    As the filter only has one match, the result of the command is equal to the result of the same command using Find-EntityView.


    The easy way:

    Luckily for us, the guys at VMware found this way of accessing commonly used objects a bit cumbersome too. So currently, 5 out of 6 managed entities can be accessed using easy-to-use cmdlets. For instance the HostSystem object I’ve explained above:

    PS P:>$esxserver001 = Get-VMHost -Name “esxserver001”

    Now that’s a lot easier, isn’t it?!


    Here’s an overview of the other cmdlets:














    Missing something? Get-Views, Get-View

    Wait a minute! Those commands áre pretty simple, but look at those output objects:

    PS P:> $esxserver001 | fl *

    State        : Connected

    CustomFields : {}

    ID           : HostSystem-host-4218

    Name         : esxserver001.domain.local

    Where are all those properties I got when usinf Get-EntityView(s)? This is pretty useless!

    Well, hold on, we need just one more step:

    PS P:>$esxserver001adv = Get-View -MoRef $esxserver001.Id

    There you go! All the properties you ever wanted.

    Let’s see what we did here. We used the Get-View cmdlet with the $esxserver001.Id property as MoRef parameter. You’ll see many cmdlets returning objects that have an .Id property. Anytime you see that, you can use Get-View to get additional properties of the object. It’s that simple. Again, Get-Views does the same trick to return a collection of objects, but I’ve never had to use it yet.


    I hope this is making at least a bit more sense to somebody than the helpfiles. I’ll post some more sample scripts soon, just to get you guys (and gals) started with some supercool scripting.

    Script on!

One thought on “Power to the API (Complete control over VMware using Powershell!)

  1. Hi Hugo

    I’ve read your article and the API reference guide but to tell you the truth I unstand the theory but didn’t really grasp how to get a list of all of the vm objects and properties of a vm.
    I’m guesing that this alone: $esxserver001adv = Get-View -MoRef $esxserver001.Id will not do anything for me with out creating an array and looping. Could you please give an example on how to get a list of all of the properties from a vm including drilling down to custom fileds and the annotation box?

    This is waht I have so far:

    $Report = @()
    $VMs = get-vmhost | Get-VM
    foreach ($VM in $VMs){
    $VMx = Get-View $VM.ID
    $HW = $VMx.guest.net
    foreach ($dev in $HW)
    foreach ($ip in $dev.ipaddress)
    $MyDetails = “” | select-Object Name, IP, MAC, OwnerDL
    $MyDetails.Name = $vm.name
    $MyDetails.IP = $ip
    $MyDetails.MAC = $dev.macaddress
    $MyDetails.MAC = $dev.OwnerDL
    $Report += $MyDetails

    Owner DL being the distribution list from the annotation box



Leave a Reply