def create_image_from_volume(self, device_name, context, image_id, image_meta): """Capture the contents of a volume and upload to glance :param device_name: device in /dev/ to capture :param context: nova context for operation :param image_id: image reference to pre-created image in glance :param image_meta: metadata for new image """ # do the disk copy dest_file_path = common.aix_path_join(CONF.powervm_img_remote_path, image_id) self._copy_device_to_file(device_name, dest_file_path) # compress and copy the file back to the nova-compute host snapshot_file_path = self._copy_image_file_from_host( dest_file_path, CONF.powervm_img_local_path, compress=True) # get glance service glance_service, image_id = glance.get_remote_image_service( context, image_id) # upload snapshot file to glance with open(snapshot_file_path, 'r') as img_file: glance_service.update(context, image_id, image_meta, img_file) LOG.debug(_("Snapshot added to glance.")) # clean up local image file try: os.remove(snapshot_file_path) except OSError as ose: LOG.warn( _("Failed to clean up snapshot file " "%(snapshot_file_path)s") % locals())
def _copy_image_file_from_host(self, remote_source_path, local_dest_dir, compress=False): """ Copy a file from IVM to the nova-compute host, and return the location of the copy :param remote_source_path remote source file path :param local_dest_dir local destination directory :param compress: if True, compress the file before transfer; if False (default), copy the file as is """ temp_str = common.aix_path_join(local_dest_dir, os.path.basename(remote_source_path)) local_file_path = temp_str + ".gz" if compress: copy_from_path = remote_source_path + ".gz" else: copy_from_path = remote_source_path if compress: # Gzip the file cmd = "/usr/bin/gzip %s" % remote_source_path self.run_vios_command_as_root(cmd) # Cleanup uncompressed remote file cmd = "/usr/bin/rm -f %s" % remote_source_path self.run_vios_command_as_root(cmd) # Get file checksum output = self._md5sum_remote_file(copy_from_path) if not output: LOG.error(_("Unable to get checksum")) msg_args = {"file_path": copy_from_path} raise exception.PowerVMFileTransferFailed(**msg_args) else: source_chksum = output.split(" ")[0] # Copy file to host common.ftp_get_command(self.connection_data, copy_from_path, local_file_path) # Calculate copied image checksum with open(local_file_path, "r") as image_file: hasher = hashlib.md5() block_size = 0x10000 buf = image_file.read(block_size) while len(buf) > 0: hasher.update(buf) buf = image_file.read(block_size) dest_chksum = hasher.hexdigest() # do comparison if source_chksum and dest_chksum != source_chksum: LOG.error(_("Image checksums do not match")) raise exception.PowerVMFileTransferFailed() # Cleanup transferred remote file cmd = "/usr/bin/rm -f %s" % copy_from_path output = self.run_vios_command_as_root(cmd) return local_file_path
def create_image_from_volume(self, device_name, context, image_id, image_meta): """Capture the contents of a volume and upload to glance :param device_name: device in /dev/ to capture :param context: nova context for operation :param image_id: image reference to pre-created image in glance :param image_meta: metadata for new image """ # do the disk copy dest_file_path = common.aix_path_join(CONF.powervm_img_remote_path, image_id) self._copy_device_to_file(device_name, dest_file_path) # compress and copy the file back to the nova-compute host snapshot_file_path = self._copy_image_file_from_host(dest_file_path, CONF.powervm_img_local_path, compress=True) # get glance service glance_service, image_id = glance.get_remote_image_service(context, image_id) # upload snapshot file to glance with open(snapshot_file_path, "r") as img_file: glance_service.update(context, image_id, image_meta, img_file) LOG.debug(_("Snapshot added to glance.")) # clean up local image file try: os.remove(snapshot_file_path) except OSError as ose: LOG.warn(_("Failed to clean up snapshot file " "%(snapshot_file_path)s") % locals())
def _copy_image_file_from_host(self, remote_source_path, local_dest_dir, compress=False): """ Copy a file from IVM to the nova-compute host, and return the location of the copy :param remote_source_path remote source file path :param local_dest_dir local destination directory :param compress: if True, compress the file before transfer; if False (default), copy the file as is """ temp_str = common.aix_path_join(local_dest_dir, os.path.basename(remote_source_path)) local_file_path = temp_str + '.gz' if compress: copy_from_path = remote_source_path + '.gz' else: copy_from_path = remote_source_path if compress: # Gzip the file cmd = "/usr/bin/gzip %s" % remote_source_path self.run_vios_command_as_root(cmd) # Cleanup uncompressed remote file cmd = "/usr/bin/rm -f %s" % remote_source_path self.run_vios_command_as_root(cmd) # Get file checksum output = self._md5sum_remote_file(copy_from_path) if not output: LOG.error(_("Unable to get checksum")) msg_args = {'file_path': copy_from_path} raise exception.PowerVMFileTransferFailed(**msg_args) else: source_chksum = output.split(' ')[0] # Copy file to host common.ftp_get_command(self.connection_data, copy_from_path, local_file_path) # Calculate copied image checksum dest_chksum = self._checksum_local_file(local_file_path) # do comparison if source_chksum and dest_chksum != source_chksum: LOG.error(_("Image checksums do not match")) raise exception.PowerVMFileTransferFailed( file_path=local_file_path) # Cleanup transferred remote file cmd = "/usr/bin/rm -f %s" % copy_from_path output = self.run_vios_command_as_root(cmd) return local_file_path
def create_image_from_volume(self, device_name, context, image_id, image_meta, update_task_state): """Capture the contents of a volume and upload to glance :param device_name: device in /dev/ to capture :param context: nova context for operation :param image_id: image reference to pre-created image in glance :param image_meta: metadata for new image :param update_task_state: Function reference that allows for updates to the instance task state. """ # Updating instance task state before capturing instance as a file update_task_state(task_state=task_states.IMAGE_PENDING_UPLOAD) # do the disk copy dest_file_path = common.aix_path_join(CONF.powervm_img_remote_path, image_id) self._copy_device_to_file(device_name, dest_file_path) # compress and copy the file back to the nova-compute host snapshot_file_path = self._copy_image_file_from_host( dest_file_path, CONF.powervm_img_local_path, compress=True) # get glance service glance_service, image_id = glance.get_remote_image_service( context, image_id) # Updating instance task state before uploading image # Snapshot will complete but instance state will not change # to none in compute manager if expected state is not correct update_task_state(task_state=task_states.IMAGE_UPLOADING, expected_state=task_states.IMAGE_PENDING_UPLOAD) # upload snapshot file to glance with open(snapshot_file_path, 'r') as img_file: glance_service.update(context, image_id, image_meta, img_file) LOG.debug(_("Snapshot added to glance.")) # clean up local image file try: os.remove(snapshot_file_path) except OSError as ose: LOG.warn(_("Failed to clean up snapshot file " "%(snapshot_file_path)s") % locals())
def test_remote_utility_4(self): path_one = '/some/file' path_two = 'path/filename' joined_path = common.aix_path_join(path_one, path_two) expected_path = '/some/file/path/filename' self.assertEqual(joined_path, expected_path)
def test_remote_utility_3(self): path_one = "/some/file" path_two = "/path/filename" joined_path = common.aix_path_join(path_one, path_two) expected_path = "/some/file/path/filename" self.assertEqual(joined_path, expected_path)