Python Libvirt Domain Configuration

So in my last article I talked a little bit about using libvirt to start and stop QEMU domains.

In this article I would like to go over how domains are created.

QEMU uses XML files for each domain configuration, and using libvirt we can access that data.

First off lets connect to our local running QEMU instance:

>>> import libvirt
>>> conn ='qemu:///system')

Next lets look for and link to a running domain:

>>> conn.listDomainsID()
[35, 36, 37, 41, 38, 39]

>>> domain = conn.lookupByID(35)

The libvirt domain object gives os a function called XMLDesc() which we can use to see our running configuration:

>>> raw_xml = domain.XMLDesc(0)
>>> print raw_xml

<domain type='kvm' id='35'>
    <type arch='x86_64' machine='fedora-13'>hvm</type>
    <boot dev='hd'/>
  <clock offset='utc'/>
    <disk type='file' device='disk'>
      <driver name='qemu' type='qcow2'/>
      <source file='/mnt/data/libvirt/datastore01/data01-dev-clone-2.img'/>
      <target dev='vda' bus='virtio'/>
      <alias name='virtio-disk0'/>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
    <disk type='file' device='cdrom'>
      <driver name='qemu' type='raw'/>
      <target dev='hdc' bus='ide'/>
      <alias name='ide0-1-0'/>
      <address type='drive' controller='0' bus='1' unit='0'/>
    <controller type='ide' index='0'>
      <alias name='ide0'/>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x1'/>
    <interface type='bridge'>
      <mac address='50:00:00:00:00:00'/>
      <source bridge='br1'/>
      <target dev='vnet0'/>
      <model type='e1000'/>
      <alias name='net0'/>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x05' function='0x0'/>
    <serial type='pty'>
      <source path='/dev/pts/0'/>
      <target port='0'/>
      <alias name='serial0'/>
    <console type='pty' tty='/dev/pts/0'>
      <source path='/dev/pts/0'/>
      <target type='serial' port='0'/>
      <alias name='serial0'/>
    <input type='tablet' bus='usb'>
      <alias name='input0'/>
    <input type='mouse' bus='ps2'/>
    <graphics type='vnc' port='5900' autoport='yes'/>
      <model type='cirrus' vram='9216' heads='1'/>
      <alias name='video0'/>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
    <memballoon model='virtio'>
      <alias name='balloon0'/>
      <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>

Now say you are interested in working with this XML data, we can do just that using the xml module:

>>> from xml.dom import minidom
>>> xml = minidom.parseString(raw_xml)

And something that may be useful in the XML above is the type tag, so lets grab that data:

>>> domainTypes = xml.getElementsByTagName('type')
>>> for domainType in domainTypes:
...   print domainType.getAttribute('machine')
...   print domainType.getAttribute('arch')

And there you have it, we can easily pull out data from this XML using the minidom function.

Using this data it should be pretty easy to deploy a new guest domain using the createXML function:

Help on method createXML in module libvirt:

createXML(self, xmlDesc, flags) method of libvirt.virConnect instance
    Launch a new guest domain, based on an XML description similar
    to the one returned by virDomainGetXMLDesc()
    This function may require privileged access to the hypervisor.
    The domain is not persistent, so its definition will disappear when it
    is destroyed, or if the host is restarted (see virDomainDefineXML() to
    define persistent domains).

    If the VIR_DOMAIN_START_PAUSED flag is set, the guest domain
    will be started, but its CPUs will remain paused. The CPUs
    can later be manually started using virDomainResume.

    If the VIR_DOMAIN_START_AUTODESTROY flag is set, the guest
    domain will be automatically destroyed when the virConnectPtr
    object is finally released. This will also happen if the
    client application crashes / loses its connection to the
    libvirtd daemon. Any domains marked for auto destroy will
    block attempts at migration, save-to-file, or snapshots.

Consuming Jenkins API using Python

Lately I’ve been using Jenkins as a central hub for automated task across multiple machines, think a central cron system with a slick web interface.

In a nutshell Jenkins CI is the leading open-source continuous integration server. Built with Java, it provides over 400 plugins to support building and testing virtually any project.

One thing that is very nice about Jenkins is the easy to use REST JSON API.

Since our Jenkins system is used internally I’ve allowed the anonymous user full read access, this allows our API read call operations in without the need to use an API KEY.

Each Jenkins page has a REST API hyperlink at the bottom, this is because each page has its own endpoint.

I’ll go over getting a list of all Projects, this uses the end point of /api/json:

>>> from urllib2 import urlopen
>>> from json import loads
>>> req = urlopen('')
>>> res =
>>> data = loads(res)

At this point we have our JSON data loaded in to a Python dict (just like every other JSON API):

>>> data.keys()
[u'unlabeledLoad', u'jobs', u'description', u'views', u'quietingDown', u'assignedLabels',
u'nodeDescription', u'useCrumbs', u'numExecutors', u'mode', u'slaveAgentPort',
u'overallLoad', u'useSecurity', u'primaryView', u'nodeName']

We can go ahead and parse over these Jobs:

>>> for job in data['jobs']:
...   print job['name']
Pull Logs from Cloud
Jenkins Job Status Notify

Or we can look directly at the dict object of the first job:

>>> data['jobs'][0].keys()
[u'url', u'color', u'name']

This will give us the full url to the job, all we need to do is append api/json to get our object:

>>> req = urlopen('%s/%s' % (data['jobs'][0]['url'], 'api/json'))
>>> res =
>>> job = loads(res)

And again we have a Python dict object:

>>> job.keys()
[u'scm', u'color', u'lastSuccessfulBuild', u'actions', u'lastCompletedBuild',
u'lastUnsuccessfulBuild', u'upstreamProjects', u'lastFailedBuild', u'healthReport',
u'queueItem', u'lastBuild', u'lastStableBuild', u'description', u'downstreamProjects',
u'concurrentBuild', u'lastUnstableBuild', u'buildable', u'displayNameOrNull',
u'inQueue', u'keepDependencies', u'name', u'displayName', u'builds', u'url',
u'firstBuild', u'nextBuildNumber', u'property']

Let say for example we want to see if the last ran build for this job was success, to do that we use the lastCompletedBuild key:

>>> job['lastCompletedBuild'].keys()
[u'url', u'number']

And like last time lets make the API call:

>>> req = urlopen('%s/%s' % (job['lastCompletedBuild']['url'], 'api/json'))
>>> res =
>>> build = loads(res)

And yet again a Python dict:

>>> build.keys()
[u'building', u'changeSet', u'builtOn', u'description', u'artifacts', u'timestamp',
u'number', u'actions', u'id', u'keepLog', u'url', u'culprits', u'result', u'executor',
u'duration', u'fullDisplayName', u'estimatedDuration']

But from here we can see the build number and status:

>>> build['number'], build['result']
(16, u'SUCCESS')

I hope this was helpful.

Diablo III API

So I was doing a bit of research on a Diablo III API, and stumbled across this article:

It seems they are still in the early stages, but there is a Character Calculator API, and it is in JSON.

First off we need to load in our Python libraries:

>>> from urllib2 import urlopen
>>> from json import loads

We can make our request using common URL methods:

>>> res = urlopen('').read()
>>> monk = loads(res)

Now we are given a simple Python dictionary:

>>> monk.keys()
[u'skills', u'traits']

And like most APIs these keys contain a list of objects:

>>> type(monk['skills'])
<type 'list'>
>>> type(monk['skills'][0])
<type 'dict'>

>>> monk['skills'][0].keys()
[u'tooltipParams', u'name', u'runes', u'simpleDescription', u'description', u'primary', u'slug',
u'requiredLevel', u'categoryName', u'categorySlug', u'icon']

So far so good, lets go ahead and itter over all our skills and get their names:

>>> for skill in sorted(monk['skills']):
...   print skill['name']
Blinding Flash
Breath of Heaven
Inner Sanctuary
Mystic Ally
Cyclone Strike
Seven-Sided Strike
Mantra of Conviction
Mantra of Healing
Mantra of Retribution
Mantra of Evasion
Deadly Reach
Way of the Hundred Fists
Fists of Thunder
Crippling Wave
Tempest Rush
Lashing Tail Kick
Wave of Light
Dashing Strike
Exploding Palm
Sweeping Wind

So there you have it, using one of the new Diablo III APIs to get class information.

Bytes, Nibbles, and Bits in Python


Binary is nothing more than a base 2 numbering system using the numbers 0 and 1.


A Bit is merely a single number of either 1 and 0 within the binary.


A Byte consists of 8 bits. A byte containing all 0s will be the integer 0, while a byte containing all 1s will be the integer of 255.


A Nibble consits of 4 bits. A nibble containing all 0s will be the iteger 0, while a nibble containing all 1s will be the integer 15 (very useful for hex numbers).

Python code

What I want to do is write a Python class for taking a valid byte (number from 0 – 255), and get its binary representation. I would also like to get the high nibble and low nibble from that binary.


Lets start by making a constructor and verifying we have a valid byte.

class Byte(object):
    """Do cool things with a 8 bit number"""

    def __init__(self, number):
        if not self.__isbyte(number):
            raise Exception('"%s" is not a 8 bit integer' % number)
        self.number = number

    def __isint(self, number):
        """Check if a input is of type int"""
        if type(number) == int:
            return True

    def __isbyte(self, number):
        """Check if a input is a byte, 0 - 255"""
        if self.__isint(number):
            if len(bin(number)[2:]) <= 8:
                return True

Alright, this code will let us define a object and verify it is a 8 bit integer.

Binary Representation

Next lets create the pretty binary representation with leading 0s as padding.

def __format(self, num, size=8):
    """Format a number as binary with leading zeros"""
    return str(bin(num)[2:]).zfill(size)

def binary(self):
    """Return Byte in binary"""
    return self.__format(self.number)

Here I wrote a small helper function for extracting the binary representation from the bin function and stripped the leading 0b. The binary property will return the binary.

High Nibble

Being all bytes are 8 bits, we can be sure a byte will have a high nibble (first 4 bits), and a low nibble (last 4 bits).

In order to get our high nibble all we need to do is use the bitwise right shift operator.

def __high_nibble(self):
    """Use Bitwise shift to get high nibble from byte"""
    return self.number >> 4

def high_nibble(self):
    """Return High Nibble in binary"""
    return self.__format(self.__high_nibble(), 4)

Low Nibble

In order to get our low nibble we can use the bitwise AND operator with a mask of 15 (remember 15 is a nibble of all 1s).

def __low_nibble(self):
    """Use Bitwise AND to get low nibble"""
    return self.number & 0x0F  # 0x0F == 15

def low_nibble(self):
    """Return Low Nibble in binary"""
    return self.__format(self.__low_nibble(), 4)

Code in action

There you have it, lets go ahead and give it a try.

In [1]: myByte = Byte(15)

In [2]: myByte.binary
Out[2]: '00001111'

In [3]: myByte.high_nibble
Out[3]: '0000'

In [4]: myByte.low_nibble
Out[4]: '1111'

Working with Libvirt using Python

Today I decide to toy around with a KVM server we have running in house for testing. I started by using the libvirt Documentation, but it was very limited and I had to do some trial and error. I will go over a few basic things I learned using the libvirt Python module:

Normally we us virt-manager to connect to our KVM instances, and the authentication is tunnled over SSH (using SSH Keys) and QEMU. First things first I had to learn how to connect with the same method we used in virt-manager:

>>> import libvirt
>>> conn ="qemu+ssh://root@")
>>> conn
<libvirt.virConnect instance at 0x2b518c0>

Using the open function I was able to successfully connect to our Hypervisor:

>>> conn.getHostname()

From here I need only see our running virtual machines, and how to interact with them. I noticed two separate function the listDefinedDomains() and listDomainsID().

These two functions do two separate things, first lets go over listDefinedDomains(), this function will return a list of offline guest by name:

>>> conn.listDefinedDomains()
['rawhide', 'el4-i386', 'el5-64', 'el6-64', ....]

Where as listDomainsID() will return a list of online devices by ID:

>>> conn.listDomainsID()
[1, 2, 10, 3, 17, 7, 9, 8, 5, 6]

Once connected to the Domain you can get its name:

>>> for i in conn.listDomainsID():
...     print conn.lookupByID(i).name()

And as you would expect you can connect to either offline or online domains by using their name:

>>> dom = conn.lookupByName('build01-dev')
>>> dom
<libvirt.virDomain instance at 0x2b82c68>

Now that we understand the process of connecting to our Hypervisor and parsing our Domains, lets go over how to start and stop these Domains, or as libvirt calls it create and destroy.

Lets start out with a offline (or destroyed) domain:

>>> dom = conn.lookupByName('rawhide')
>>> dom.isActive()

To bring this Domain online we need to use the create() function:

>>> dom.create()
>>> dom.isActive()

And to power it down you would destroy() it:

>>> dom.destroy()
>>> dom.isActive()

I hope this helped out a few of you out there, I know this was rather confusion when I first started messing around with it.