LibvirtXMLConfigAPIs

The libvirt driver in Essex and earlier uses the Cheetah templating engine to generate the guest XML config from a canned template. There are a number of problems with this approach


 * No XML escaping takes place. This will lead to future security vulnerabilities if we are not very careful
 * The logic for constructing the XML is split across multiple areas of the code, the template file and the connection driver which populates template variables. This needlessly complicates the code and makes it harder to understand the overall logic used to generate the XML
 * It is hard to modularize code for generating XML sensibly. For example, disk XML generation is duplicated between the XML template & the volume.py class
 * There is no object model for the libvirt driver code to work against. Everything has to invent its own ad-hoc XML parser / misc XPath queries

These problems are only going to get worse over time, leading to the conclusion that using a templating engine is a doomed approach overall.

The way to solve this problem is to introduce a formal object model describing the libvirt guest configuration. The driver code will interact exclusively with the object model reading/writing properties / child objects as required. Once the object model is complete, it can simply serialize itself straight to XML using the lxml DOM APIs. The benefits this will bring are


 * Guaranteed correct escaping of all XML elements/attributes
 * No need for any driver code to know about XML parsing or formatting
 * Concentration of logic for generating the guest config in one place
 * Facilitate modularization of the config generation code
 * Facilitate the testing of the config generation code

The outline for the object model hiearchy is as follows

LibvirtConfigObject |   + LibvirtConfigGuest + LibvirtConfigGuestDevice |       +- LibvirtConfigGuestDisk +- LibvirtConfigGuestFilesys +- LibvirtConfigGuestInterface +- LibvirtConfigGuestInput +- LibvirtConfigGuestGraphics +- LibvirtConfigGuestChar |           +- LibvirtConfigGuestSerial +- LibvirtConfigGuestConsole

This need not be confined to just the libvirt guest XML. Other XML documents related to libvirt will similarly benefit, eg CPU config, host capabilties, domain snapshots, etc

The rough scope of changes is as follows


 * nova/virt/libvirt.xml.template: Delete file & associated FLAGS.libvirt_xml_template
 * nova/virt/cpuinfo.xml.template: Delete file & associated FLAGS.cpuinfo_xml_template
 * nova/virt/connection.py: Replace _prepare_xml_info method which returns a dict of template parameters, with a get_guest_config method which returns a LibvirtConfigGuest object
 * nova/virt/config.py: Create set of objets for representing the libvirt guest config & related XML documents (see above class hierarchy)
 * nova/virt/vif.py: Change _get_configurations methods to return LibvirtConfigGuestInterface objects
 * nova/virt/volume.py: Change connect_volume methods to return LibvirtConfigGuestDisk objects

Some background discussions


 * https://lists.launchpad.net/openstack/msg08408.html
 * https://lists.launchpad.net/openstack/msg06481.html

Corresponding blueprint


 * https://blueprints.launchpad.net/nova/+spec/libvirt-xml-config-apis