Introduction

Programing with the VMware Java SDK can be a real pain. Retrieving a simple property on a VMware object requires lot of lines of code. We will try the VI Java API which is a set of Java libraries that sits on top of the existing vSphere SDK Web Services interface.

In order to retrieve properties, perform operations or modify entities within the vSphere API, it is important to understand the vSphere Object Model's structure and relationships. The vSphere API consists of three types of objects:

Imagine you want to get the names of all hosts in the inventory, or maybe you want to monitor for changes to the power state of all VMs in the inventory, or you want to keep track of the host that each VM is running on, you have to use the Property Collector.

The PropertyCollector gives you the ability to retrieve properties of the ManagedObject and also monitor the changes of any properties you interested in.

In order to use the PropertyCollector to retrieve informations from Managed Object, you need to specify what data you want to retrieve and this is done with something called PropertyFilterSpec and this object has at least 2 properties:

And those objects have other objects as parameter,and you need to create. Obviously, you see that it requires many lines of code before retrieving the name of a VM or whatever properties you want to get from your vCenter.

vijava (Virtual Infrastructure API) is an open source project created by Steve Jin from VMware R&D. It aims to simplify the use of VI SDK and improve the performance.

This API encapsulate the PropertyCollector behind Java methods and provide a whole bunch of ManagedObject that will allow you to manipulate vmware objects without any effort.

The picture below represent the object architecture that will be very helpful to code you program and you will see further in this article that I manipulate those objects to retrieve specific properties.

Good Practices


The overall object model

The above can be inferred from our VI SDK API reference. Please note that we don't have a managed object type called ManagedObject in our reference. This is a type defined to capture all the common properties and behaviors of all managed objects. Given the limited size, I only show the names of the types, not properties and methods.

To better group these managed object types, I used colors. On the right most side of the diagram are the ServiceInstance class and various "manager" classes like AuthorizationManager. From the ServiceInstance, you can get any object of these types with single call, for example getAuthorizationManager().

In the middle of left side, you can find ManagedEntity class and its sub-classes like HostSystem, VirtualMachine. These classes represent all the items you could find in the inventory tree from VI client. They are the most important managed objects in the whole model, and all tagged with orange color except the HostSystem.

The HostSystem is very much like ServiceInstance in that it has many "System" or "Manager" types closely attached to it, for example, HostDatastoreSystem. You can get hold of these objects with a single method call from a HostSystem object. For this reason, both HostSystem and all the attached classes are tagged the same color.

...

A detailed partial UML diagram

...

This UML diagram is extracted from the overall model but adds much more details with properties and methods. If you can understand this diagram, you can then easily understand all the other managed object types.
The ManagedObject class holds two private properties:
  1. mor of type ManagedObjectReference -- pointing to the ManagedObjectReference object that is used to represent a managed object in VI SDK.
  2. serverConnection of type ServerConnection -- pointing to the ServerConnection object I will cover later.

Besides accessors, the class has getCurrentProperty() method defined to encapsulate the PropertyCollector. This method gets called in subclasses to get a property. For example, the getName() in ManagedEntity called it like (String) getCurrentProperty("name"); In most of cases, you don't need to use it at all, I already provide explicit getter methods in concrete subclasses.

The ServerConnection is used to represent a connection to the server under a specific login user. It holds information like url to the server, the userSession with username etc., and vimService which is the JUMBO interfaces with 300+ methods. For convenience, ServerConnection also has a reference to a ServiceInstance object.

Now let us take a look at the ServiceInstance type. It's a special managed object and the first managed object you will have in a typical application logic flow. You can create a new ServiceInstance object by providing url/username/password, or url/sessionID combination. The later is not used as much as the first constructor, but very helpful when you develop a VI client plugin in Java.

According to the API reference, the ServiceInstance has a ServiceContent object as its property, which holds all the ManagedObjectReferences to various "manager" attached to it, and an AboutInfo data object. Unlike web service interface, you can get any of them with a single call in Java API. ServiceContent object is, therefore, no long needed, and I don't even provide a getter to it.

At the right side of the diagram are the ExtensibleManagedObject and its subclass ManagedEnity. ExtensibleManagedObject doesn't have methods defined at all, but three properties. Therefore it only has three corresponding getters. As you will find in the overall UML diagram, it has many other subclasses, but I only list the ManagedEntity here.

ManagedEntity is one of the most important managed object type given that VirtualMachine, HostSystem etc. are all inherited from it. To search the inventory, I also provide a utility like class InventoryNavigator to group all the search methods to retrieve items in the inventory tree from a specified node. For example, you can easily find all the Virtual in one single call.

The above two ML diagrams should have given you a big picture about the object model and how key types are related to each other. If you really need to know more details, please download the latest jar file. It has all the binary, source code and some sample code.


Example 1: Connect to the ServiceInstance of your ESXi
public ServiceInstance Initialisation(String url, String username, String password)
 throws RemoteException, MalformedURLException {
  ServiceInstance si = new ServiceInstance(new URL(url), username, password, true);
  return si;
}

This is the method you can use to connect your ESXI servive. The initialization method takes 3 parameters which are: This method will return a ServiceInstance object which will be used to have access to your VMware object tree (see the picture).
Example 2: Retrieve ManagedEntity from Inventory Navigator
public ManagedEntity[] RetreiveVM(ServiceInstance si) throws InvalidProperty, RuntimeFault, RemoteException{
  ManagedEntity[] mes = new InventoryNavigator(si.getRootFolder()).searchManagedEntities("VirtualMachine");
  return mes;
}

This method takes the ServiceInstance object that we had in the previous section. Here we have to create a rootFolder object from our ServiceInstance object.
And next we can already retrieve ManagedObject (VirtualMachine in my exemple) with the searchManagedEntities method and fill the mes[] table with all the VMs of your infrastructure.
From the InventoryNavigator object, you can use: With these methods, you can already retrieve VMs from your vCenter. The next will be to retrieve information of the VM and you will see that in the next section.
Example 3: Convert ManagedEntity object and retrieve VM properties
public void setSelectedVM(int index) {
  VirtualMachine vm = (VirtualMachine) mes[index];
  System.out.println("Guest OS:"+vm.getSummary().getConfig().guestFullName);
}

First of all, you will have to convert the "mes" object into a "virtualMachine" object. Then you are free to exploit the hundreds of properties of the VM object.

The VirtualMachine Class

List of Main Class

Others


Example 4: Retrieve hardware properties
for (VirtualDevice vd : vm.getConfig().getHardware().getDevice()) {
  try {
   if (vd instanceof VirtualEthernetCard) {
    VirtualEthernetCard vEth = (VirtualEthernetCard) vd;
  } catch (Exception e) {
 }
}
you can easily get the following hardware devices: VideoCard, VMCIDevice, VirtualSCSIPassThrough, VirtualDisk, VirtualCdrom and VirtualEthernetCard.
VirtualEthernetCard vEth = (VirtualEthernetCard) vd;
  System.out.println("connected"+vEth.getConnectable().connected);
  System.out.println("Connect at power on"+vEth.getConnectable().startConnected);
  System.out.println("Manual"+vEth.addressType);
  System.out.println("MAC address:"+vEth.macAddress);
You are now able to read properties of every single object by following this technique and the picture in section 2. However, some of the advanced hardware properties are tricky to find and it can take long before you find out the right object to use.