OpaqueRef and uuid relationship in xapi
When someone starts to work with XenAPI he founds strange 'OpaqueRef' objects in relationship fields instead expected UUIDs.
UUIDs used as unique identificator in 'xe' CLI, so everyone starts to convert OpaqueRef to UUIDs. This take some resources and slow down operations.
Actually, UUID is not the 'core' identificator of objects, it just something like 'name-label', but more unique. It can be found in 'natural' form as domain handler (libxc), as filename/logical volume label for VID in SR/SM implementation and so on. In certain cases it can be even change during object lifetime (for example, when you import vm with uuid preservation, xapi create vm with some random UUID and change it to required later).
But xapi use OpaqueRef as real object identificator, the primary key in internal xapi database. When one object points to other it does not say 'link=uuid', it says 'link=opaqueref'.
So, for purposes of relationship management OpaqueRef is enough. Conversion to uuid shall be used for:
- User interaction (most for 'xe' CLI)
- XC interaction for VM object ('handle' field of domain_getinfo)
- lowlevel SR operations (outside xapi)
- ... and other out-of-xapi things
Here some quotes of Dave Scott from xen-api maillist about OpaqueRefs:
Here's a brief history of what happened: First we wanted to create an API for managing VMs, VIFs, VBDs etc. We thought we would have VMs etc being objects and "references" would be the primary way to name them. We wanted to reserve the right to change what a reference looks like, so that we could maybe encode some (eg) security-related information (like a capability) or some scope-related information (eg if you had nested pools) in the future. To discourage people from looking at the actual strings too much, we put the prefix "OpaqueRef" on as a warning :) So far, everything is relatively clean. Since xen domains have uuids, we added a VM.uuid field. I think we also added a VDI.uuid field at this point -- with hindsight this was a mistake. We believed that each storage type could use a uuid to identify a disk but it turned out that some storage types had nowhere convenient to actually store the information so it could be retrieved efficiently. We added a VDI.location field to contain the most appropriate primary key to identify a VDI within an SR and the VDI.uuid field became a bit vestigial. So far, everything is still ok. We then started developing the "xe" cli. At this point we made the crucial decision that OpaqueRef: strings were just too visually ugly to use in a commandline interface and decided to name objects by uuid. This was fine for VMs and VDIs but nothing else had a uuid field. Inevitably we then added uuids to other objects so now they're almost ubiquitous. Now we have two parallel object naming mechanisms which is a bit strange. My current rule of thumb is that: whenever I'm using the XenAPI directly (eg in python) I will use refs exclusively (no uuids). When I write scripts that use the "xe" CLI I will use uuids exclusively (no refs). Does that make sense (even if it is a little bit unfortunate!)?
About OpaqueRef persistence:
Although we've always been hesitant to guarantee this, as you've noted we use the OpaqueRef as the primary key inside our database. Plus we have never changed them and realistically I think we will never need to change them. Plus it is very convenient to be able to cache them-- I'm keen to exploit this to make the event mechanism more efficient. So I believe storing OpaqueRefs (instead of uuids) is a safe thing to do.