Add Custom Fields to VI Client with Powershell (Samples)

In my previous post, I showed you how to add information to your VI Client using Custom Fields. Here are some ready-to-go scripts to add very useful info:

Snapshot Count

I already showed you how to do this, but I have now added an IF-statement so that only changes are updated (equal values are not overwritten). And I have added Julian Wood’s correction. add-vmsnapshotcount (rename to .ps1)

Total Snapshot Size

The number of snapshots is quite inetresting, but even more interesting, is the total size of the delta files all snapshots are occupying. They might be eating up all your precious SAN space. Plus, reverting to or committing a large snapshot is tricky. add-vmsnapshotsize1 (rename to .ps1)

Host Hardware Model

Want to see what models of hardware you are using in your datacenter? You could look at the summary tab of each host. Or run this script to add the info to the every Hosts tab in the VI Client. Select your Datacenter, select the Hosts tab and enjoy! add-vmhostmodel (rename to .ps1)

Host ESX Version

Did you update all your ESX Servers to the latest version? Check it quickly using this script. add-vmhostversion (rename to .ps1)

Host LUN Count

Last but certainly not least: are you sure every datastore you are using is available to all your ESX Servers? It is visible at a glance when you add the LUN Count to your VI Client! add-vmhostluncount (rename to .ps1)

Happy Holidays!


38 thoughts on “Add Custom Fields to VI Client with Powershell (Samples)

  1. Oh my G! Sorry about that!
    Seems like the WordPress 2.7 media uploader doesn’t really like .ps1 files. I have now changed them all to txt files and I have checked that they are all available.

  2. I must be stupid… but I am getting errors when I run this. I am running it on my VC server with PS and vm toolkit installed. What else do I need for these scripts to run correctly. It actually connects with the VC and adds the custom field but it does not fill it with data. I get lots of the following:

    + $VMView.setCustomValue( <<<< $CustomFieldName,$SnapShotCount)
    Get-Snapshot : 12/17/2008 11:59:45 AM Get-Snapshot not connected
    At C:\DOCUME~1\slanger1\LOCALS~1\Temp\cb6eb088-c077-4600-958d-b49c6d3c2dcf.ps1:
    47 char:31
    + $SnapshotCount = (Get-Snapshot <<<< -VM $VM | Measure-Object).Count
    Get-View : 12/17/2008 11:59:45 AM Get-View not connected
    At C:\DOCUME~1\slanger1\LOCALS~1\Temp\cb6eb088-c077-4600-958d-b49c6d3c2dcf.ps1:
    48 char:25
    + $VMView = $VM | Get-View <<<<
    Exception calling “setCustomValue” with “2” argument(s): “The session is not au
    At C:\DOCUME~1\slanger1\LOCALS~1\Temp\cb6eb088-c077-4600-958d-b49c6d3c2dcf.ps1:
    49 char:23
    + $VMView.setCustomValue( <<<< $CustomFieldName,$SnapShotCount)
    Get-Snapshot : 12/17/2008 11:59:46 AM Get-Snapshot not connected
    At C:\DOCUME~1\slanger1\LOCALS~1\Temp\cb6eb088-c077-4600-958d-b49c6d3c2dcf.ps1:
    47 char:31
    + $SnapshotCount = (Get-Snapshot <<<< -VM $VM | Measure-Object).Count
    Get-View : 12/17/2008 11:59:46 AM Get-View not connected
    At C:\DOCUME~1\slanger1\LOCALS~1\Temp\cb6eb088-c077-4600-958d-b49c6d3c2dcf.ps1:
    48 char:25
    + $VMView = $VM | Get-View <<<<

  3. @scott
    Scott, I guess I am the stupid one… I forgot to remove some temporary lines from the end of the script. I should start triplechecking my posts… 🙁 Very sorry about that.
    I have updated the script. Try refreshing your view in the VI Client (Press F5). And remember only non-zero values will be filled in.

  4. these are really cool – thanks – what if i have a text file with two field – the name of the VM and the value for a custom field called “vm usage” – can i use this file to fill in the VC client ?. if so how ?.

    Many thanks

  5. Hi Hugo – super quick response ! basically the txt file is like:

    Name vm usage
    VM1 backup box
    VM2 Firewall test

    the “vm usage” is the current custom field we have in VC. I can get this file as a CSV and massage the content however really.

  6. Great, if you have it as a csv, you can do:
    $vmtexts = Import-Csv PATHTOTHEFILE.csv
    Then, if I assume the csv has columns named NAME and VMUSAGE (I removed the space from vm usage, to make the script a bit simpler):
    ForEach ($vmtext in $vmtexts)
    $VM = Get-VM $
    $VMView = $VM | Get-View
    $VMView.setCustomValue(“vm usage”,$vmtext.vmusage)

  7. @Matt
    You’re welcome.
    That depends a bit on how they are listed in the text file. Is it a csv?
    Creating and filling in the fields is just some small modifications in the scripts I posted. If you supply a sample of the text file, I’ll gladly post the resulting script for you.

  8. Hi Hugo, I’m completly new to this powershell stuff, so maybe this is an easy one: Played around with the snapshot count script but I’m always getting:

    Get-Snapshot : Value cannot be found for the mandatory parameter VM
    At C:\add-vmsnapshotcount.ps1:29 char:32
    + $SnapshotCount = (Get-Snapshot <<<< -VM $VM | Measure-Object).Count

    Any ideas?


  9. Thanks Hugo for all the scripts…amazing…what a help

    I’ve thought of another potential issue with updating the Snapshot details in VC.
    You pull in all the VMs and then check whether a snapshot exists before checking whether the values are different.

    $SnapshotCount = (Get-Snapshot -VM $VM | Measure-Object).Count
    If ($SnapShotCount)

    If a VM had snapshots and they are all removed before the script is run, VC won’t be updated with the value of 0 as the update only happens if the VM currently has snapshots. You could still be left with Snapshot count values in VC when there are no longer snapshots.

    I’ve tried to factor this in in a script but if I try to read the value and it is not set or even try to compare it to $Null I get an error.
    Any idea how you can check the setting of the CustomField if it has not previously been set?

    You cannot call a method on a null-valued expression.
    At line:1 char:22

    Could you also please explain how this line works:
    If ($SnapShotCount -ne ($VMView.CustomValue | ?{$_.Key -eq $myCustomField.Key}).Value)

    What is the? and why do you need to link back to the $myCustomField.Key rather than just comparing
    If ($SnapShotCount -ne $vm.CustomFields.Item($CustomFieldName))

    Thanks again for all the help, Hugo.

  10. Hi Julian,
    I had to read your comment four times to really understand what your mean. But you are absolutely right. My logic is based on filling the information for the first time, in which case you can afford to do nothing if no snapshots exist. But if they did exist previously and the custom field is filled, I should not skip the vm with no snapshots. So the “If ($SnashotCount){}” should go out the window. It became obsolute anyway when I added the part that checks if the new value is different from the old value.
    Here how the compare works:
    $VMView.CustomValue is an array with custom fields. I need the one that corresponds to the field we are filling. But the names of the fields are not there. But there is a Key, which is unique. The ? is shorthand for “Where”. So $VMView.CustomValue | ?{$_.Key -eq $myCustomField.Key} returns only the custom field with the right Key. I Compare the snapshotcount to the value of that custom field.
    Hope this makes sense to you.

  11. Hugo – I was looking for your script to add RDM sizes to the VI client, I don’t see it posted here. Is this still available?


  12. […] Link | VMware Infrastructure Power Documenter Link | ESX Automated Configuration Midwife Link | Add Custom Fields to VI Client with Powershell Link | VMware Health Check Script Link | Track Datastore Free Space Link | List disk RDMS Link | […]

  13. Guys,

    I need assistance with a script that can create to Custom Fields in Virtual Center (Total Disk Allocated) (Total Disk Free). The Total Disk Allocated and Total Disk Free must be in GB and combine all drives (c:, D;. E: etc, /boot, /, etc)

    I would like to use icoma’s power scripter to automate the script on daily basis on each datacenters/clusters.

  14. Hugo – I ran the hostluncount script and it worked. However, everyone who logs into my virtual center see’s it too. How can I remove the field now! lol, sorry!

  15. @kdonofrio
    $VCServerName = “MYVCSERVER”
    $CustomFieldName = “LUNs”
    $VC = Connect-VIServer $VCServerName
    $SI = Get-View ServiceInstance
    $CFM = Get-View $SI.Content.CustomFieldsManager
    $myCustomField = $CFM.Field | Where {$_.Name -eq $CustomFieldName}
    If ($myCustomField)

  16. I almost have this.. but what if I want to edit or place information in a custom field of a specific vm (TESTDPLY-VT01) where the custom field already exists. EX:
    I have the custom fields named:
    How do I edit those…
    I thought I had it..but I was wrong..
    I am guessing the NOTE field is edited differently…
    Thank you

  17. @Glen
    $VM = Get-VM “MY_VM”
    $VMView = $VM | Get-View

    The note field: Set-VM “MY_VM” -Description “My_NewValue”

  18. Great Job, I am new to all of this scripting and love it. Your scripts are great. Just have a question, I put in the custom fields for total snapshots and snapshot size. When I view at a site location that shows all of my virtual machines the fields are not populated. When I drill down to a cluster level the fields are populated. Is ther another command I need to ad to populate at the site level?

  19. Hello ! Great Job,

    how is it possible to determine in this script that the custom field is only changed for a special data center or cluster.

    many thanks in advance.

    best regards

    • Hello Methone,
      You can modify the line below # Fill Custom Fields to make sure only a few VMs or VMHosts are included. For instance:
      $VMHosts = Get-VMHost -Location (Get-Cluster “MyCluster”)
      $VMs = Get-VM -Location (Get-VMHost “ESX12”)

      Hope this helps,

  20. Hello !
    thanks ! I tried it with cluster and it works. Is there also a way to fill the custom field for templates ?
    Best regards

  21. Hi there,
    since our migation to vSphere i get the following error when i run your skript:

    Exception calling “SearchDatastoreSubFolders” with “2” argument(s): “Not initialized: boolean fileOwner”
    At :line:33 char:53
    + $searchResult = $dsBrowser.SearchDatastoreSubFolders <<<< ($SnapshotDirectory, $searchSpec)

    You have any idea for me?

    Best regards

    • That’s new since vSphere 4.0. Behind this line:
      $fileQueryFlags.FileSize = $true
      Add the following line:
      $fileQueryFlags.FileOwner = $false

      This tells the SearchDatastore method not to return file owners in the query.

  22. Hello,

    I’ve succesfully implemented a couple of scripts that added some extra custom fields to my vm’s.

    If i am cloning some vm’s to another datacenter/vcenter the custom fields won’t be copied. Is it possible that i can export and import the custom fields to the notes (annotation) field for every VM.

    Thanks in advance.


Leave a Reply