def _parse_df_output(output): """ This method parses the output of 'df -hT' command. :param output: Parsed output of the 'df -hT' command :return:list containing filesystems information """ try: output = output.splitlines() out_list = [] for fs in output[1:]: fs_dict = {} fs_list = fs.split() fs_dict['filesystem'] = fs_list[0] fs_dict['type'] = fs_list[1] fs_dict['size'] = int(fs_list[2]) fs_dict['used'] = fs_list[3] fs_dict['avail'] = int(fs_list[4]) fs_dict['use%'] = fs_list[5] fs_dict['mounted_on'] = fs_list[6] out_list.append(fs_dict) except: wok_log.error("Parsing df output failed") raise OperationFailed("GINFS00003E") return out_list
def upgrade_objectstore_data(item, old_uri, new_uri): """ Upgrade the value of a given JSON's item of all Template and VM entries of the objectstore from old_uri to new_uri. """ total = 0 try: conn = sqlite3.connect(config.get_object_store(), timeout=10) cursor = conn.cursor() sql = "SELECT id, json FROM objects WHERE type='template' OR type='vm'" cursor.execute(sql) for row in cursor.fetchall(): # execute update here template = json.loads(row[1]) path = template[item] if item in template else 'none' if path.startswith(old_uri): template[item] = new_uri + path sql = 'UPDATE objects SET json=?, version=? WHERE id=?' cursor.execute( sql, (json.dumps(template), config.get_kimchi_version(), row[0]) ) conn.commit() total += 1 except sqlite3.Error as e: if conn: conn.rollback() wok_log.error('Error while upgrading objectstore data: %s', e.args[0]) raise OperationFailed('KCHUTILS0006E') finally: if conn: conn.close() wok_log.info("%d '%s' entries upgraded in objectstore.", total, item)
def activate(self, ifacename): wok_log.info('Bring up an interface ' + ifacename) iface_type = netinfo.get_interface_type(ifacename) if iface_type == "Ethernet": cmd_ipup = ['ip', 'link', 'set', '%s' % ifacename, 'up'] out, error, returncode = run_command(cmd_ipup) if returncode != 0: wok_log.error( 'Unable to bring up the interface on ' + ifacename + ', ' + error) raise OperationFailed('GINNET0059E', {'name': ifacename, 'error': error}) # Some times based on system load, it takes few seconds to # reflect the /sys/class/net files upon execution of 'ip link # set' command. Following snippet is to wait util files get # reflect. timeout = self.wait_time(ifacename) if timeout == 5: wok_log.warn("Time-out has happened upon execution of 'ip " "link set <interface> up', hence behavior of " "activating an interface may not as expected.") else: wok_log.info( 'Successfully brought up the interface ' + ifacename) wok_log.info('Activating an interface ' + ifacename) cmd_ifup = ['ifup', '%s' % ifacename] out, error, returncode = run_command(cmd_ifup) if returncode != 0: wok_log.error( 'Unable to activate the interface on ' + ifacename + ', ' + error) raise OperationFailed('GINNET0016E', {'name': ifacename, 'error': error}) wok_log.info( 'Connection successfully activated for the interface ' + ifacename)
def lookup(self, path): try: path_components = utils.validate_lun_path(path) return utils.get_lun_info(*path_components) except ValueError: wok_log.error("Fetching LUN info failed, %s", path) raise NotFoundError("GS390XSTG00008", {'path': path})
def delete(self, name): try: fs_utils.unpersist_swap_dev(name) utils._swapoff_device(name) except Exception as e: wok_log.error("Error deleting a swap device, %s", e.message) raise OperationFailed("GINSP00009E", {'err': e.message})
def parse_lsblk_out(lsblk_out): """ Parse the output of 'lsblk -Po' :param lsblk_out: output of 'lsblk -Po' :return: Dictionary containing information about disks on the system """ try: out_list = lsblk_out.splitlines() return_dict = {} for disk in out_list: disk_info = {} disk_attrs = disk.split() disk_type = disk_attrs[1] if not disk_type == 'TYPE="disk"': continue if len(disk_attrs) == 4: disk_info['transport'] = disk_attrs[3].split("=")[1][1:-1] else: disk_info['transport'] = "unknown" disk_info['size'] = disk_attrs[2].split("=")[1][1:-1] return_dict[disk_attrs[0].split("=")[1][1:-1]] = disk_info except Exception as e: wok_log.error("Error parsing 'lsblk -Po") raise OperationFailed("GINSD00004E", {'err': e.message}) return return_dict
def stop(self, params=None): cmd = ['systemctl', 'stop', 'sepctl'] output, error, rc = run_command(cmd) if rc != 0: wok_log.error('Error stopping SEP service: %s - %s - %s' % (cmd, rc, error)) raise OperationFailed('GINSEP0009E', {'error': error})
def _get_subscriber(self): activation_info = [] entry = {} cmd = ['/opt/ibm/seprovider/bin/getSubscriber'] output, error, rc = run_command(cmd) # no subscriber: return empty if rc == 1: return activation_info # error: report if rc != 0: wok_log.error('SEP execution error: %s - %s - %s' % (cmd, rc, error)) raise OperationFailed('GINSEP0007E') if len(output) > 1: # iterate over lines and parse to dict for line in output.splitlines(): if len(line) > 0: entry = SUBSCRIBER.search(line).groupdict() activation_info.append(entry["hostname"]) return activation_info
def lookup(self, subscription): """ Returns a dictionary with all SEP information. """ cmd = ['/opt/ibm/seprovider/bin/getSubscriber'] output, error, rc = run_command(cmd) # error: report if rc != 0: wok_log.error('SEP execution error: %s - %s - %s' % (cmd, rc, error)) raise OperationFailed('GINSEP0005E', {'error': error}) if len(output) > 1: # iterate over lines and parse to dict for line in output.splitlines(): if len(line) > 0: entry = SUBSCRIBER.search(line).groupdict() # subscriber found if entry["hostname"] == subscription: return entry raise NotFoundError("GINSEP0006E", {'hostname': subscription})
def start(self, params=None): cmd = ['systemctl', 'start', 'sepctl'] output, error, rc = run_command(cmd) if rc != 0: wok_log.error('SEP service initialization error: %s - %s - %s' % (cmd, rc, error)) raise OperationFailed('GINSEP0008E', {'error': error})
def get_list(self, _configured=None): """ :param _configured: True will list only the network devices which are configured. znetconf -c will be used False will list only network devices which are not configured yet. znetconf -u will be used If not given then it will fetch both the list of devices. :return: network OSA device info list. """ wok_log.info('Fetching network devices. _configured ' '= %s' % _configured) if _configured is None: devices = _get_configured_devices() devices.extend(_get_unconfigured_devices()) elif _configured in ['True', 'true']: devices = _get_configured_devices() elif _configured in ['False', 'false']: devices = _get_unconfigured_devices() else: wok_log.error("Invalid _configured given. _configured: %s" % _configured) raise InvalidParameter("GS390XINVTYPE", {'supported_type': 'True/False'}) wok_log.info('Successfully retrieved network devices') return devices
def get_disk_used_by(objstore, conn, path): try: with objstore as session: try: used_by = session.get("storagevolume", path)["used_by"] except (KeyError, NotFoundError): wok_log.info("Volume %s not found in obj store." % path) used_by = [] # try to find this volume in existing vm vms_list = VMsModel.get_vms(conn) for vm in vms_list: dom = VMModel.get_vm(vm, conn) storages = get_vm_disks(dom) for disk in storages.keys(): d_info = get_vm_disk_info(dom, disk) if path == d_info["path"]: used_by.append(vm) try: session.store("storagevolume", path, {"used_by": used_by}, get_kimchi_version()) except Exception as e: # Let the exception be raised. If we allow disks' # used_by to be out of sync, data corruption could # occour if a disk is added to two guests # unknowingly. wok_log.error("Unable to store storage volume id in" " objectstore due error: %s", e.message) raise OperationFailed("KCHVOL0017E", {"err": e.message}) except Exception as e: # This exception is going to catch errors returned by 'with', # specially ones generated by 'session.store'. It is outside # to avoid conflict with the __exit__ function of 'with' raise OperationFailed("KCHVOL0017E", {"err": e.message}) return used_by
def _create_ifcfg_file(interface): """ method to create ifcfg-enccw<device_id> file in /etc/sysconfig/network-scripts/ folder and change persmission of that file to 644 to be in sync with other files in directory :param interface: network device id :return: None """ wok_log.info('creating ifcfg file for %s', interface) ifcfg_file_path = '/' + ifcfg_path.replace('<deviceid>', interface) try: ifcfg_file = open(ifcfg_file_path, 'w+') ifcfg_file.close() os.system('chmod 644 ' + ifcfg_file_path) wok_log.info('created file %s for network device %s' % (ifcfg_file_path, interface)) except Exception as e: wok_log.error('failed to create file %s for network device %s. ' 'Error: %s' % (ifcfg_file_path, interface, e.__str__())) raise OperationFailed("GS390XIONW005E", {'ifcfg_file_path': ifcfg_file_path, 'device': interface, 'error': e.__str__()})
def _validate_device(interface): """ validate the device id. Valid device Ids should have <single digitnumber>.<single digitnumber>.<4 digit hexadecimalnumber> or <4 digit hexadecimal number> :param interface: device id """ wok_log.info('Validating network interface %s' % interface) pattern_with_dot = r'^\d\.\d\.[0-9a-fA-F]{4}$' if interface and not str(interface).isspace(): interface = str(interface).strip() if ENCCW in interface: interface = interface.strip(ENCCW) out = re.search(pattern_with_dot, interface) if out is None: wok_log.error("Invalid interface id. interface: %s" % interface) raise InvalidParameter("GS390XINVINPUT", {'reason': 'invalid interface id: %s' % interface}) wok_log.info('Successfully validated network interface') else: wok_log.error("interface id is empty. interface: %s" % interface) raise InvalidParameter("GS390XINVINPUT", {'reason': 'device id is required. ' 'device id: %s' % interface})
def _format_znetconf(device): """ method to reform dictionary with new keys for znetconf devices :param device: device dictionary with keys " ZNETCONF_STATE, ZNETCONF_DEV_IDS, ZNETCONF_CARDTYPE, ZNETCONF_CHPID, ZNETCONF_DRV, ZNETCONF_TYPE, ZNETCONF_DEV_NAME, :return: dictionary with new keys mapped as follows ZNETCONF_STATE - "state", ZNETCONF_DEV_IDS - "device_ids", ZNETCONF_CARDTYPE- "card_type" ZNETCONF_CHPID - "chpid", ZNETCONF_DRV - "driver", ZNETCONF_TYPE - "type", ZNETCONF_DEV_NAME - "name", ZNETCONF_CHPID - "chipid" ZNETCONF_STATE if not present then its set as Un-configured. As for configured device, state can be both Online and Offline And for un configured, state is not returned in znetconf -u ZNETCONF_DEV_NAME is mapped to "name" and if ZNETCONF_DEV_NAME is not present then "name" value is set as one of the device from the list of deviceIds """ if device: try: device['state'] = device.pop(ZNETCONF_STATE, 'Unconfigured') device_ids = list(device.pop(ZNETCONF_DEV_IDS).split(',')) device['device_ids'] = device_ids device['card_type'] = device.pop(ZNETCONF_CARDTYPE) device['chpid'] = device.pop(ZNETCONF_CHPID) device['driver'] = device.pop(ZNETCONF_DRV) device['type'] = device.pop(ZNETCONF_TYPE) device['name'] = device.pop(ZNETCONF_DEV_NAME, device_ids[0]) except KeyError as e: wok_log.error('Issue while formatting znetconf dictionary output') raise e return device
def lookup(self, name): try: return utils._vgdisplay_out(name) except OperationFailed: wok_log.error('failed to fetch vg info') raise NotFoundError("GINVG00003E", {'name': name})
def _is_dev_extended_partition(devType, devNodePath): if devType != 'part': return False if devNodePath.startswith('/dev/mapper'): try: dev_maj_min = _get_dev_major_min(devNodePath.split("/")[-1]) parent_sys_path = '/sys/dev/block/' + dev_maj_min + '/slaves' parent_dm_name = os.listdir(parent_sys_path)[0] parent_maj_min = open( parent_sys_path + '/' + parent_dm_name + '/dev').readline().rstrip() diskPath = _get_dev_node_path(parent_maj_min) except Exception as e: wok_log.error( "Error dealing with dev mapper device: " + devNodePath) raise OperationFailed("GGBDISK00001E", {'err': e.message}) else: diskPath = devNodePath.rstrip('0123456789') device = PDevice(diskPath) try: extended_part = PDisk(device).getExtendedPartition() except NotImplementedError as e: wok_log.warning( "Error getting extended partition info for dev %s type %s: %s", devNodePath, devType, e.message) # Treate disk with unsupported partiton table as if it does not # contain extended partitions. return False if extended_part and extended_part.path == devNodePath: return True return False
def get_dev_info(node_dev): ''' Parse the node device XML string into dict according to http://libvirt.org/formatnode.html. scsi_generic is not documented in libvirt official website. Try to parse scsi_generic according to the following libvirt path series. https://www.redhat.com/archives/libvir-list/2013-June/msg00014.html scsi_target is not documented in libvirt official website. Try to parse scsi_target according to the libvirt commit db19834a0a. ''' xmlstr = node_dev.XMLDesc(0) info = dictize(xmlstr)['device'] dev_type = info['capability'].pop('type') info['device_type'] = dev_type cap_dict = info.pop('capability') info.update(cap_dict) # parent device not found: set as None info["parent"] = info.get("parent") if dev_type in ('scsi', 'scsi_generic', 'scsi_target', 'system', 'usb'): return info if dev_type in ('net', 'pci', 'scsi_host', 'storage', 'usb_device'): return globals()['_get_%s_dev_info' % dev_type](info) wok_log.error("Unknown device type: %s", dev_type) return info
def disable_tcp_port(port): _, err, r_code = run_command( ['firewall-cmd', '--remove-port=%s/tcp' % port] ) if r_code != 0: wok_log.error('Error when removing port from ' 'firewall-cmd: %s' % err)
def lookup(self, name): try: return utils._pvdisplay_out(name) except OperationFailed: wok_log.error("Unable to fetch details of PV") raise NotFoundError("GINPV00004E", {'name': name})
def _generate_thumbnail(self): thumbnail = os.path.join(config.get_screenshot_path(), '%s-%s.png' % (self.vm_uuid, str(uuid.uuid4()))) self._get_test_result() if stream_test_result is None: self._watch_stream_creation(thumbnail) elif stream_test_result: try: self._generate_scratch(thumbnail) except: wok_log.error("screenshot_creation: Unable to create " "screenshot image %s." % thumbnail) else: self._create_black_image(thumbnail) if os.path.getsize(thumbnail) == 0: self._create_black_image(thumbnail) else: im = Image.open(thumbnail) try: # Prevent Image lib from lazy load, # work around pic truncate validation in thumbnail generation im.thumbnail(self.THUMBNAIL_SIZE) except Exception as e: wok_log.warning("Image load with warning: %s." % e) im.save(thumbnail, "PNG") self.info['thumbnail'] = thumbnail
def __exit__(self, type, value, tb): self._lock.release() if type is not None and issubclass(type, sqlite3.DatabaseError): # Logs the error and return False, which makes __exit__ raise # exception again wok_log.error(traceback.format_exc()) return False
def delete(self, name): try: utils.delete_part(name) except OperationFailed as e: wok_log.error("delete partition failed") raise OperationFailed("GINPART00007E", {'err': e})
def parse_hdds(temperature_unit): # hddtemp will strangely convert a non-number (see error case # below) to 32 deg F. So just always ask for C and convert later. out, error, rc = run_command(['hddtemp']) if rc: wok_log.error("Error retrieving HD temperatures: rc %s." "output: %s" % (rc, error)) return None hdds = OrderedDict() for hdd in out.splitlines(): hdd_name = '' hdd_temp = 0.0 try: hdd_items = hdd.split(':') hdd_name, hdd_temp = hdd_items[0], hdd_items[2] hdd_temp = re.sub('°[C|F]', '', hdd_temp).strip() except Exception as e: wok_log.error('Sensors hdd parse error: %s' % e.message) continue try: # Try to convert the number to a float. If it fails, # don't add this disk to the list. hdd_temp = float(hdd_temp) if(temperature_unit == 'F'): hdd_temp = 9.0/5.0 * hdd_temp + 32 hdds[hdd_name] = hdd_temp except ValueError: # If no sensor data, parse float will fail. For example: # "/dev/sda: IBM IPR-10 5D831200: S.M.A.R.T. not available" wok_log.warning("Sensors hdd: %s" % hdd) hdds['unit'] = temperature_unit return hdds
def _validate_device(device): """ validate the device id. Valid device Ids should have <single digitnumber>.<single digitnumber>.<4 digit hexadecimalnumber> or <4 digit hexadecimal number> :param device: device id """ pattern_with_dot = r'^\d\.\d\.[0-9a-fA-F]{4}$' if isinstance(device, unicode): # str() on non ascii non encoded cannot be done device = device.encode('utf-8') if device and not str(device).isspace(): device = str(device).strip() if "." in device: out = re.search(pattern_with_dot, device) else: device = '0.0.' + device out = re.search(pattern_with_dot, device) if out is None: wok_log.error("Invalid device id. Device: %s" % device) raise InvalidParameter("GS390XINVINPUT", {'reason': 'invalid device id: %s' % device}) else: wok_log.error("Device id is empty. Device: %s" % device) raise InvalidParameter("GS390XINVINPUT", {'reason': 'device id is required. Device: %s' % device}) return device
def delete(self, vm_name, dev_name): try: bus_type = self.lookup(vm_name, dev_name)['bus'] dom = VMModel.get_vm(vm_name, self.conn) except NotFoundError: raise if (bus_type not in HOTPLUG_TYPE and DOM_STATE_MAP[dom.info()[0]] != 'shutoff'): raise InvalidOperation('KCHVMSTOR0011E') try: disk = get_device_node(dom, dev_name) path = get_vm_disk_info(dom, dev_name)['path'] if path is None or len(path) < 1: path = self.lookup(vm_name, dev_name)['path'] # This has to be done before it's detached. If it wasn't # in the obj store, its ref count would have been updated # by get_disk_used_by() if path is not None: used_by = get_disk_used_by(self.objstore, self.conn, path) else: wok_log.error("Unable to decrement volume used_by on" " delete because no path could be found.") dom.detachDeviceFlags(etree.tostring(disk), get_vm_config_flag(dom, 'all')) except Exception as e: raise OperationFailed("KCHVMSTOR0010E", {'error': e.message}) if used_by is not None and vm_name in used_by: used_by.remove(vm_name) set_disk_used_by(self.objstore, path, used_by) else: wok_log.error("Unable to update %s:%s used_by on delete." % (vm_name, dev_name))
def _get_deviceinfo(lscss_out, device): """ :param lscss_out: out of lscss command :param device: device id for which we need info to be returned :return: device info dict for the device from lscss output """ device_pattern = r'(' + re.escape(device) + r')\s+' \ r'(\d\.\d\.[0-9a-fA-F]{4})\s+' \ r'(\w+\/\w+)\s+' \ r'(\w+\/\w+)\s' \ r'(\s{3}|yes)\s+' \ r'([0-9a-fA-F]{2})\s+' \ r'([0-9a-fA-F]{2})\s+' \ r'([0-9a-fA-F]{2})\s+' \ r'(\w+\s\w+)' if device: device = utils.get_row_data(lscss_out, HEADER_PATTERN, device_pattern) msg = 'The device is %s' % device wok_log.debug(msg) try: device_info = _format_lscss(device) return device_info except KeyError as e: wok_log.error('lscss column key not found') raise e else: return device
def _get_resources(self, flag_filter): try: get_list = getattr(self.model, model_fn(self, 'get_list')) idents = get_list(*self.model_args, **flag_filter) res_list = [] for ident in idents: # internal text, get_list changes ident to unicode for sorted args = self.resource_args + [ident] res = self.resource(self.model, *args) try: res.lookup() except Exception as e: # In case of errors when fetching a resource info, pass and # log the error, so, other resources are returned # Encoding error message as ident is also encoded value. # This has to be done to avoid unicode error, # as combination of encoded and unicode value results into # unicode error. wok_log.error("Problem in lookup of resource '%s'. " "Detail: %s" % (ident, encode_value(e.message))) continue res_list.append(res) return res_list except AttributeError: return []
def get_mlx5_nic_type(mlx5_iface): """Checks lspci output to see if mlx5_iface is a physical or virtual nic interface. This is the lspci output this function is expecting for a mlx5 virtual nic interface: 'Ethernet controller: Mellanox Technologies MT27700 Family [ConnectX-4 Virtual Function]' Verification will be done by checking for the 'Virtual Function' string in the output. Any other lspci output format or any other error will make this function return the default value 'physical'. Args: mlx5_iface (str): interface loaded by the mlx5_core driver. Returns: str: 'virtual' if mlx5_iface is a virtual function/nic, 'physical' otherwise. """ bus_id = get_mlx5_nic_bus_id(mlx5_iface) lspci_cmd = ['lspci', '-s', bus_id] out, err, r_code = run_command(lspci_cmd) if r_code == 0 and 'Virtual Function' in out: return 'virtual' if r_code != 0: wok_log.error('Error while getting nic type of ' 'interface: %s' % err) return 'physical'
def get_iommu_group(dev_info): # Find out the iommu group of a given device. # Child device belongs to the same iommu group as the parent device. try: return dev_info['iommuGroup'] except KeyError: pass parent = dev_info['parent'] while parent is not None: try: parent_info = dev_dict[parent] except KeyError: wok_log.error("Parent %s of device %s does not exist", parent, dev_info['name']) break try: iommuGroup = parent_info['iommuGroup'] except KeyError: pass else: return iommuGroup parent = parent_info['parent'] return None
class StoragePoolsModel(object): def __init__(self, **kargs): self.conn = kargs['conn'] self.objstore = kargs['objstore'] self.scanner = Scanner(self._clean_scan) self.scanner.delete() self.caps = CapabilitiesModel(**kargs) self.device = DeviceModel(**kargs) if self.conn.get() is not None: if self.conn.isQemuURI(): self._check_default_pools() def _check_default_pools(self): pools = {} default_pool = tmpl_defaults['disks'][0]['pool']['name'] default_pool = default_pool.split('/')[-1] pools[default_pool] = {} if default_pool == 'default': pools[default_pool] = {'path': '/var/lib/libvirt/images'} if config.get('kimchi', {}).get('create_iso_pool', False): pools['ISO'] = {'path': '/var/lib/kimchi/isos'} error_msg = ("Please, check the configuration in %s/template.conf to " "ensure it has a valid storage pool." % kimchiPaths.sysconf_dir) conn = self.conn.get() for pool_name in pools: try: pool = conn.storagePoolLookupByName(pool_name) except libvirt.libvirtError, e: pool_path = pools[pool_name].get('path') if pool_path is None: msg = "Fatal: Unable to find storage pool %s. " + error_msg wok_log.error(msg % pool_name) wok_log.error("Details: %s", e.message) sys.exit(1) # Try to create the pool pool = E.pool(E.name(pool_name), type='dir') pool.append(E.target(E.path(pool_path))) xml = ET.tostring(pool) try: pool = conn.storagePoolDefineXML(xml, 0) except libvirt.libvirtError, e: msg = "Fatal: Unable to create storage pool %s. " msg += error_msg wok_log.error(msg % pool_name) wok_log.error("Details: %s", e.message) sys.exit(1) # Build and set autostart value to pool # Ignore error as the pool was already successfully created try: # Add build step to make sure target directory created # The build process may fail when the pool directory # already exists on system pool.build(libvirt.VIR_STORAGE_POOL_BUILD_NEW) pool.setAutostart(1) except: pass if pool.isActive() == 0: try: pool.create(0) except libvirt.libvirtError, e: msg = "Fatal: Unable to craete storage pool %s. " msg += error_msg wok_log.error(msg % pool_name) wok_log.error("Details: %s", e.message) sys.exit(1)
def sosreport_generate(cb, name): def log_error(e): log = logging.getLogger('Model') log.warning('Exception in generating debug file: %s', e) try: command = ['sosreport', '--batch', '--name=%s' % name] output, error, retcode = run_command(command) if retcode != 0: raise OperationFailed("KCHDR0003E", { 'name': name, 'err': retcode }) # SOSREPORT might create file in /tmp or /var/tmp # FIXME: The right way should be passing the tar.xz file directory # though the parameter '--tmp-dir', but it is failing in Fedora 20 patterns = ['/tmp/sosreport-%s-*', '/var/tmp/sosreport-%s-*'] reports = [] reportFile = None for p in patterns: reports = reports + [f for f in glob.glob(p % name)] for f in reports: if not fnmatch.fnmatch(f, '*.md5'): reportFile = f break # Some error in sosreport happened if reportFile is None: wok_log.error( 'Debug report file not found. See sosreport ' 'output for detail:\n%s', output) fname = (patterns[0] % name).split('/')[-1] raise OperationFailed('KCHDR0004E', {'name': fname}) md5_report_file = reportFile + '.md5' report_file_extension = '.' + reportFile.split('.', 1)[1] path = config.get_debugreports_path() target = os.path.join(path, name + report_file_extension) # Moving report msg = 'Moving debug report file "%s" to "%s"' % (reportFile, target) wok_log.info(msg) shutil.move(reportFile, target) # Deleting md5 msg = 'Deleting report md5 file: "%s"' % (md5_report_file) wok_log.info(msg) with open(md5_report_file) as f: md5 = f.read().strip() wok_log.info('Md5 file content: "%s"', md5) os.remove(md5_report_file) cb('OK', True) return except WokException as e: log_error(e) raise except OSError as e: log_error(e) raise except Exception, e: # No need to call cb to update the task status here. # The task object will catch the exception raised here # and update the task status there log_error(e) raise OperationFailed("KCHDR0005E", {'name': name, 'err': e})
'item': str(item), 'name': name }) if name in self.get_list(): raise InvalidOperation("KCHPOOL0001E", {'name': name}) try: if task_id: # Create transient pool for deep scan conn.storagePoolCreateXML(xml, 0) return name pool = conn.storagePoolDefineXML(xml, 0) except libvirt.libvirtError as e: wok_log.error("Problem creating Storage Pool: %s", e) raise OperationFailed("KCHPOOL0007E", { 'name': name, 'err': e.get_error_message() }) # Build and set autostart value to pool # Ignore error as the pool was already successfully created # The build process fails when the pool directory already exists try: if params['type'] in ['logical', 'dir', 'netfs', 'scsi']: pool.build(libvirt.VIR_STORAGE_POOL_BUILD_NEW) pool.setAutostart(1) else: pool.setAutostart(0) except:
def _create_volume_with_url(self, cb, params): pool_name = params['pool'] name = params['name'] url = params['url'] pool_model = StoragePoolModel(conn=self.conn, objstore=self.objstore) pool = pool_model.lookup(pool_name) if pool['type'] in ['dir', 'netfs']: file_path = os.path.join(pool['path'], name) else: file_path = tempfile.mkstemp(prefix=name)[1] with contextlib.closing(urllib2.urlopen(url)) as response: with open(file_path, 'w') as volume_file: remote_size = response.info().getheader('Content-Length', '-') downloaded_size = 0 try: while True: chunk_data = response.read(READ_CHUNK_SIZE) if not chunk_data: break volume_file.write(chunk_data) downloaded_size += len(chunk_data) cb('%s/%s' % (downloaded_size, remote_size)) except (IOError, libvirt.libvirtError) as e: if os.path.isfile(file_path): os.remove(file_path) raise OperationFailed('KCHVOL0007E', { 'name': name, 'pool': pool_name, 'err': e.message }) if pool['type'] in ['dir', 'netfs']: virt_pool = StoragePoolModel.get_storagepool(pool_name, self.conn) virt_pool.refresh(0) else: def _stream_handler(stream, nbytes, fd): return fd.read(nbytes) virt_stream = virt_vol = None try: task = self.create( pool_name, { 'name': name, 'format': 'raw', 'capacity': downloaded_size, 'allocation': downloaded_size }) self.task.wait(task['id']) virt_vol = StorageVolumeModel.get_storagevolume( pool_name, name, self.conn) virt_stream = self.conn.get().newStream(0) virt_vol.upload(virt_stream, 0, downloaded_size, 0) with open(file_path) as fd: virt_stream.sendAll(_stream_handler, fd) virt_stream.finish() except (IOError, libvirt.libvirtError) as e: try: if virt_stream: virt_stream.abort() if virt_vol: virt_vol.delete(0) except libvirt.libvirtError, virt_e: wok_log.error(virt_e.message) finally: raise OperationFailed('KCHVOL0007E', { 'name': name, 'pool': pool_name, 'err': e.message }) finally: