[libvirt] [test-API][PATCH v2] Add test case update_devflag.py for update device flag

--- repos/domain/update_devflag.py | 163 ++++++++++++++++++++++++++++++++++++++++ 1 files changed, 163 insertions(+), 0 deletions(-) create mode 100644 repos/domain/update_devflag.py diff --git a/repos/domain/update_devflag.py b/repos/domain/update_devflag.py new file mode 100644 index 0000000..287f2a5 --- /dev/null +++ b/repos/domain/update_devflag.py @@ -0,0 +1,163 @@ +#!/usr/bin/evn python +"""Update virtual device to guest from an XML file +""" + +__author__ = 'Nan Zhang: nzhang@redhat.com' +__date__ = 'Fri Sep 2, 2011' +__version__ = '0.1.0' +__credits__ = 'Copyright (C) 2011 Red Hat, Inc.' +__all__ = ['usage', 'update_devflag'] + +import os +import re +import sys +import commands +from xml.dom import minidom + +def append_path(path): + """Append root path of package""" + if path in sys.path: + pass + else: + sys.path.append(path) + +pwd = os.getcwd() +result = re.search('(.*)libvirt-test-API', pwd) +append_path(result.group(0)) + +from lib import connectAPI +from lib import domainAPI +from utils.Python import utils +from utils.Python import xmlbuilder +from exception import LibvirtAPI + +def usage(): + print '''usage: mandatory arguments: + guestname + devtype + ''' + +def check_params(params): + """Verify inputing parameter dictionary""" + logger = params['logger'] + keys = ['guestname', 'devtype'] + for key in keys: + if key not in params: + logger.error("%s is required" %key) + usage() + return 1 + return 0 + +def create_image(params, img_name, img_size): + """Create an image file""" + logger = params['logger'] + stat, ret = commands.getstatusoutput("dd if=/dev/zero of=%s bs=1 \ + count=1 seek=%s" % (img_name, img_size)) + if stat == 0: + logger.debug("create image result:\n%s" % ret) + return True + else: + return False + +def check_updated_device(params, guestname, domobj, srcfile): + """Check if the device is updated""" + logger = params['logger'] + xmlobj = domobj.get_xml_desc(guestname) + domxml = minidom.parseString(xmlobj) + + for diskTag in domxml.getElementsByTagName("source"): + if diskTag.parentNode.getAttribute("device") == 'cdrom': + upfile = diskTag.getAttribute("file") + elif diskTag.parentNode.getAttribute('device') == 'floppy': + upfile = diskTag.getAttribute("file") + + if upfile == srcfile: + return False, upfile + else: + return True, upfile + +def update_devflag(params): + """Update virtual device to a domain from xml""" + + # Initiate and check parameters + params_check_result = check_params(params) + if params_check_result: + return 1 + logger = params['logger'] + guestname = params['guestname'] + devtype = params['devtype'] + if devtype == 'cdrom': + xmlargs = {} + xmlargs['guestname'] = guestname + xmlargs['guesttype'] = 'kvm' + xmlargs['hdmodel'] = 'ide' + xmlargs['bootcd'] = '/var/lib/libvirt/boot/cdrom.img' + srcfile = xmlargs['bootcd'] + create_image(params, srcfile, '100M') + elif devtype == 'floppy': + xmlargs = {} + xmlargs['guestname'] = guestname + xmlargs['floppysource'] = '/var/lib/libvirt/boot/floppy.img' + srcfile = xmlargs['floppysource'] + create_image(params, srcfile, '2M') + else: + srcfile = None + logger.error("Wrong device type was specified.") + return 1 + + if not params.has_key('flag'): + flag = domainAPI.VIR_DOMAIN_AFFECT_CONFIG + + # Connect to local hypervisor connection URI + util = utils.Utils() + uri = util.get_uri('127.0.0.1') + conn = connectAPI.ConnectAPI() + virconn = conn.open(uri) + + caps = conn.get_caps() + logger.debug(caps) + + # Generate device XML for updating + domobj = domainAPI.DomainAPI(virconn) + newxmlobj = xmlbuilder.XmlBuilder() + + if devtype == 'cdrom': + newdevxml = newxmlobj.build_cdrom(xmlargs) + elif devtype == 'floppy': + newdevxml = newxmlobj.build_floppy(xmlargs) + + logger.debug("block device xml desc:\n%s" %newdevxml) + + try: + try: + domobj.update_device_flag(guestname, newdevxml, flag) + res, upfile = check_updated_device(params, guestname, \ + domobj, srcfile) + if res: + logger.info("success to update '%s' device: %s\n" % \ + (devtype, upfile)) + else: + logger.error("fail to update '%s' device: %s\n" % \ + (devtype, upfile)) + except LibvirtAPI, e: + logger.error("API error message: %s, error code is %s" % + (e.response()['message'], e.response()['code'])) + conn.close() + logger.info("closed hypervisor connection") + return 1 + finally: + conn.close() + logger.info("closed hypervisor connection") + + return 0 + +def update_devflag_clean(params): + """Clean testing environment""" + logger = params['logger'] + + if params['devtype'] == 'cdrom': + os.unlink('/var/lib/libvirt/boot/cdrom.img') + elif params['devtype'] == 'floppy': + os.unlink('/var/lib/libvirt/boot/floppy.img') + else: + logger.debug("image file was not found.") -- 1.7.4.4

On 09/08/2011 11:29 AM, Nan Zhang wrote:
--- repos/domain/update_devflag.py | 163 ++++++++++++++++++++++++++++++++++++++++ 1 files changed, 163 insertions(+), 0 deletions(-) create mode 100644 repos/domain/update_devflag.py
diff --git a/repos/domain/update_devflag.py b/repos/domain/update_devflag.py new file mode 100644 index 0000000..287f2a5 --- /dev/null +++ b/repos/domain/update_devflag.py @@ -0,0 +1,163 @@ +#!/usr/bin/evn python +"""Update virtual device to guest from an XML file +""" + +__author__ = 'Nan Zhang: nzhang@redhat.com' +__date__ = 'Fri Sep 2, 2011' +__version__ = '0.1.0' +__credits__ = 'Copyright (C) 2011 Red Hat, Inc.' +__all__ = ['usage', 'update_devflag'] + +import os +import re +import sys +import commands +from xml.dom import minidom + +def append_path(path): + """Append root path of package""" + if path in sys.path: + pass + else: + sys.path.append(path) + +pwd = os.getcwd() +result = re.search('(.*)libvirt-test-API', pwd) +append_path(result.group(0)) + +from lib import connectAPI +from lib import domainAPI +from utils.Python import utils +from utils.Python import xmlbuilder +from exception import LibvirtAPI + +def usage(): + print '''usage: mandatory arguments: + guestname + devtype + ''' + I think this is not the good way to show the help message. Defining it in the description is better like this. """ Update virtual device to guest from an XML file domain:update_devflag guestname xxx devtype cdrom|floppy """ +def check_params(params): + """Verify inputing parameter dictionary""" + logger = params['logger'] + keys = ['guestname', 'devtype'] + for key in keys: + if key not in params: + logger.error("%s is required" %key) + usage() + return 1 + return 0 + +def create_image(params, img_name, img_size): + """Create an image file""" + logger = params['logger'] + stat, ret = commands.getstatusoutput("dd if=/dev/zero of=%s bs=1 \ + count=1 seek=%s" % (img_name, img_size)) + if stat == 0: + logger.debug("create image result:\n%s" % ret) + return True + else: + return False + +def check_updated_device(params, guestname, domobj, srcfile): + """Check if the device is updated""" + logger = params['logger'] + xmlobj = domobj.get_xml_desc(guestname) + domxml = minidom.parseString(xmlobj) + + for diskTag in domxml.getElementsByTagName("source"): + if diskTag.parentNode.getAttribute("device") == 'cdrom': + upfile = diskTag.getAttribute("file") + elif diskTag.parentNode.getAttribute('device') == 'floppy': + upfile = diskTag.getAttribute("file") + + if upfile == srcfile: + return False, upfile + else: + return True, upfile
The checking the simple, at least we should login to the guest, to check if the device could be functional like being mounted successfully.
+ +def update_devflag(params): + """Update virtual device to a domain from xml""" + + # Initiate and check parameters + params_check_result = check_params(params) + if params_check_result: + return 1 + logger = params['logger'] + guestname = params['guestname'] + devtype = params['devtype']
The update-device is for inactive domain, so we need to check if the domain given is in right state.
+ if devtype == 'cdrom': + xmlargs = {} + xmlargs['guestname'] = guestname + xmlargs['guesttype'] = 'kvm' + xmlargs['hdmodel'] = 'ide' + xmlargs['bootcd'] = '/var/lib/libvirt/boot/cdrom.img' + srcfile = xmlargs['bootcd'] + create_image(params, srcfile, '100M')
It's better to check the return value of create_image.
+ elif devtype == 'floppy': + xmlargs = {} + xmlargs['guestname'] = guestname + xmlargs['floppysource'] = '/var/lib/libvirt/boot/floppy.img' + srcfile = xmlargs['floppysource'] + create_image(params, srcfile, '2M')
same like above
+ else: + srcfile = None + logger.error("Wrong device type was specified.") + return 1 + + if not params.has_key('flag'): + flag = domainAPI.VIR_DOMAIN_AFFECT_CONFIG + + # Connect to local hypervisor connection URI + util = utils.Utils() + uri = util.get_uri('127.0.0.1') + conn = connectAPI.ConnectAPI() + virconn = conn.open(uri) + + caps = conn.get_caps() + logger.debug(caps) + + # Generate device XML for updating + domobj = domainAPI.DomainAPI(virconn) + newxmlobj = xmlbuilder.XmlBuilder()
Before generating new device xml description, the domain have to the original xml definition first for update, from your testing scenario, you need to check the domain with the original device xml defined.
+ + if devtype == 'cdrom': + newdevxml = newxmlobj.build_cdrom(xmlargs) + elif devtype == 'floppy': + newdevxml = newxmlobj.build_floppy(xmlargs) + + logger.debug("block device xml desc:\n%s" %newdevxml) + + try: + try: + domobj.update_device_flag(guestname, newdevxml, flag) + res, upfile = check_updated_device(params, guestname, \ + domobj, srcfile) + if res: + logger.info("success to update '%s' device: %s\n" % \ + (devtype, upfile)) + else: + logger.error("fail to update '%s' device: %s\n" % \ + (devtype, upfile)) + except LibvirtAPI, e: + logger.error("API error message: %s, error code is %s" % + (e.response()['message'], e.response()['code'])) + conn.close() + logger.info("closed hypervisor connection") + return 1 + finally: + conn.close() + logger.info("closed hypervisor connection") + + return 0 + +def update_devflag_clean(params): + """Clean testing environment""" + logger = params['logger'] + + if params['devtype'] == 'cdrom': + os.unlink('/var/lib/libvirt/boot/cdrom.img') + elif params['devtype'] == 'floppy': + os.unlink('/var/lib/libvirt/boot/floppy.img') + else: + logger.debug("image file was not found.")
When I run you testcase, there is also some errors, please fix it. Guannan Ren

--- repos/domain/update_devflag.py | 231 ++++++++++++++++++++++++++++++++++++++++ 1 files changed, 231 insertions(+), 0 deletions(-) create mode 100644 repos/domain/update_devflag.py diff --git a/repos/domain/update_devflag.py b/repos/domain/update_devflag.py new file mode 100644 index 0000000..3b736fc --- /dev/null +++ b/repos/domain/update_devflag.py @@ -0,0 +1,231 @@ +#!/usr/bin/env python +"""Update virtual device to guest from an XML file + domain:update_devflag + guestname + xxx + devtype + cdrom|floppy +""" + +__author__ = 'Nan Zhang: nzhang@redhat.com' +__date__ = 'Fri Sep 2, 2011' +__version__ = '0.1.0' +__credits__ = 'Copyright (C) 2011 Red Hat, Inc.' +__all__ = ['check_updated_device', 'update_devflag'] + +import os +import re +import sys +import time +import subprocess +from xml.dom import minidom + +qemu_img_bin = "/usr/bin/qemu-img" + +def append_path(path): + """Append root path of package""" + if path in sys.path: + pass + else: + sys.path.append(path) + +pwd = os.getcwd() +result = re.search('(.*)libvirt-test-API', pwd) +append_path(result.group(0)) + +from lib import connectAPI +from lib import domainAPI +from utils.Python import utils +from utils.Python import xmlbuilder +from exception import LibvirtAPI + +def qemu_img(*args): + global qemu_img_bin + + devnull = open('/dev/null', 'r+') + return subprocess.call([qemu_img_bin] + list(args), stdin=devnull, \ + stdout=devnull) + +def check_params(params): + """Verify inputing parameter dictionary""" + logger = params['logger'] + keys = ['guestname', 'devtype'] + for key in keys: + if key not in params: + logger.error("%s is required" %key) + return 1 + return 0 + +def create_image(params, img_name, img_size): + """Create an image file""" + logger = params['logger'] + ret = qemu_img('create', '-f', 'raw', img_name, img_size) + + if ret == 0: + logger.debug("create an image %s with %s." % (img_name, img_size)) + return True + else: + logger.error("image creation fail.") + return False + +def check_device_in_guest(params, util, guestip): + """Check updated device in guest""" + logger = params['logger'] + + if params['devtype'] == 'cdrom': + cmd = "mount -o loop /dev/cdrom /media" + elif params['devtype'] == 'floppy': + cmd = "mount /dev/fd0 /media" + else: + logger.error("it's not a cdrom or floppy device.") + return False, None + + ret, output = util.remote_exec_pexpect(guestip, "root", "redhat", cmd) + logger.debug(output) + if ret: + logger.error("failed to mount %s device." % params['devtype']) + return False, output + + time.sleep(5) + + ret, output = util.remote_exec_pexpect(guestip, "root", "redhat", \ + "umount /media") + logger.debug(output) + if ret: + logger.error("failed to unmount %s device." % params['devtype']) + return False, output + + time.sleep(5) + + ret, output = util.remote_exec_pexpect(guestip, "root", "redhat", \ + "ls /media") + logger.debug(output) + if ret: + logger.error("failed to list contents of %s device." \ + % params['devtype']) + return False, output + + return True, output + +def check_updated_device(params, output, util, guestip, domobj, srcfile): + """Check if the device is updated""" + logger = params['logger'] + xmlobj = domobj.get_xml_desc(params['guestname']) + domxml = minidom.parseString(xmlobj) + + for diskTag in domxml.getElementsByTagName("source"): + if diskTag.parentNode.getAttribute("device") == 'cdrom': + upfile = diskTag.getAttribute("file") + elif diskTag.parentNode.getAttribute('device') == 'floppy': + upfile = diskTag.getAttribute("file") + + res = check_device_in_guest(params, util, guestip) + if res[0] and cmp(res[1], output): + if upfile == srcfile: + logger.error("checking fail.") + return False, upfile + else: + logger.info("checking successful.") + return True, upfile + else: + return False, None + +def update_devflag(params): + """Update virtual device to a domain from xml""" + + # Initiate and check parameters + params_check_result = check_params(params) + if params_check_result: + return 1 + + logger = params['logger'] + guestname = params['guestname'] + devtype = params['devtype'] + + if devtype == 'cdrom': + xmlargs = {} + xmlargs['guestname'] = guestname + xmlargs['guesttype'] = 'kvm' + xmlargs['hdmodel'] = 'ide' + xmlargs['bootcd'] = '/var/lib/libvirt/boot/cdrom.img' + srcfile = xmlargs['bootcd'] + if not create_image(params, srcfile, '100M'): + return 1 + elif devtype == 'floppy': + xmlargs = {} + xmlargs['guestname'] = guestname + xmlargs['floppysource'] = '/var/lib/libvirt/boot/floppy.img' + srcfile = xmlargs['floppysource'] + if not create_image(params, srcfile, '2M'): + return 1 + else: + srcfile = None + logger.error("Wrong device type was specified.") + return 1 + + if not params.has_key('flag'): + flag = domainAPI.VIR_DOMAIN_AFFECT_CONFIG + + # Connect to local hypervisor connection URI + util = utils.Utils() + uri = util.get_uri('127.0.0.1') + mac = util.get_dom_mac_addr(guestname) + guestip = util.mac_to_ip(mac, 180) + logger.debug("ip address: %s" % guestip) + + ret, output = check_device_in_guest(params, util, guestip) + logger.debug(output) + if not ret: + return 1 + + conn = connectAPI.ConnectAPI() + virconn = conn.open(uri) + caps = conn.get_caps() + logger.debug(caps) + + # Generate device XML for updating + domobj = domainAPI.DomainAPI(virconn) + newxmlobj = xmlbuilder.XmlBuilder() + + if devtype == 'cdrom': + newdevxml = newxmlobj.build_cdrom(xmlargs) + elif devtype == 'floppy': + newdevxml = newxmlobj.build_floppy(xmlargs) + + logger.debug("block device xml desc:\n%s" % newdevxml) + logger.debug("domain xml before updating:\n%s" \ + % domobj.get_xml_desc(guestname)) + + try: + domobj.update_device_flag(guestname, newdevxml, flag) + logger.debug("domain xml after updating:\n%s" \ + % domobj.get_xml_desc(guestname)) + res, upfile = check_updated_device(params, output, util, \ + guestip, domobj, srcfile) + if res: + logger.info("success to update '%s' device: %s\n" % \ + (devtype, upfile)) + else: + logger.error("fail to update '%s' device: %s\n" % \ + (devtype, upfile)) + conn.close() + logger.info("closed hypervisor connection") + except LibvirtAPI, e: + logger.error("API error message: %s, error code is %s" % + (e.response()['message'], e.response()['code'])) + conn.close() + logger.info("closed hypervisor connection") + return 1 + + return 0 + +def update_devflag_clean(params): + """Clean testing environment""" + logger = params['logger'] + + if params['devtype'] == 'cdrom': + os.unlink('/var/lib/libvirt/boot/cdrom.img') + elif params['devtype'] == 'floppy': + os.unlink('/var/lib/libvirt/boot/floppy.img') + else: + logger.debug("image file was not found.") -- 1.7.4.4
participants (2)
-
Guannan Ren
-
Nan Zhang