def configure_container_configdrive(self, container_config, instance, injected_files): LOG.debug('Creating LXD config drive') if CONF.config_drive_format not in ('fs', None): msg = (_('Invalid config drive format: %s') % CONF.config_drive_format) raise exception.InstancePowerOnFailure(reason=msg) LOG.info(_LI('Using config drive for instance'), instance=instance) extra_md = {} inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md) name = instance.name try: with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: container_configdrive = ( self.container_dir.get_container_configdrive(name) ) cdb.make_drive(container_configdrive) container_config = self.configure_disk_path(container_config, 'configdrive', instance) except Exception as e: with excutils.save_and_reraise_exception(): LOG.error(_LE('Creating config drive failed with error: %s'), e, instance=instance) return container_config
def _generate_configdrive(self, instance, node, network_info, extra_md=None, files=None): """Generate a config drive. :param instance: The instance object. :param node: The node object. :param network_info: Instance network information. :param extra_md: Optional, extra metadata to be added to the configdrive. :param files: Optional, a list of paths to files to be added to the configdrive. """ if not extra_md: extra_md = {} i_meta = instance_metadata.InstanceMetadata(instance, content=files, extra_md=extra_md, network_info=network_info) with tempfile.NamedTemporaryFile() as uncompressed: with configdrive.ConfigDriveBuilder(instance_md=i_meta) as cdb: cdb.make_drive(uncompressed.name) with tempfile.NamedTemporaryFile() as compressed: # compress config drive with gzip.GzipFile(fileobj=compressed, mode='wb') as gzipped: uncompressed.seek(0) shutil.copyfileobj(uncompressed, gzipped) # base64 encode config drive compressed.seek(0) return base64.b64encode(compressed.read())
def fake_InstanceMetadata(stubs, inst_data, address=None, sgroups=None, content=None, extra_md=None, vd_driver=None, network_info=None, network_metadata=None): content = content or [] extra_md = extra_md or {} if sgroups is None: sgroups = [dict(test_security_group.fake_secgroup, name='default')] def sg_get(*args, **kwargs): return sgroups stubs.Set(api, 'security_group_get_by_instance', sg_get) return base.InstanceMetadata(inst_data, address=address, content=content, extra_md=extra_md, vd_driver=vd_driver, network_info=network_info, network_metadata=network_metadata)
def _create_config_drive(self, context, instance_path, instance, injected_files, admin_password): if CONF.config_drive_format not in ['tgz', 'iso9660']: msg = (_("Invalid config drive format %s") % CONF.config_drive_format) LOG.debug(msg) raise exception.ConfigDriveUnsupportedFormat( format=CONF.config_drive_format) LOG.debug('Using config drive', instance=instance) extra_md = {} if admin_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, request_context=context) # network_metadata will prevent the hostname of the instance from # being set correctly, so clean the value inst_md.network_metadata = None configdrive_tgz = os.path.join(instance_path, 'cfgdrive.tgz') LOG.debug('Creating config drive at %s', configdrive_tgz, instance=instance) with zvmconfigdrive.ZVMConfigDriveBuilder(instance_md=inst_md) as cdb: cdb.make_drive(configdrive_tgz) return configdrive_tgz
def _create_config_drive(context, instance_path, instance, injected_files, network_info, admin_password): if CONF.config_drive_format != 'iso9660': raise exception.ConfigDriveUnsupportedFormat( format=CONF.config_drive_format) LOG.debug('Using config drive', instance=instance) extra_md = {} if admin_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info, request_context=context) configdrive_iso = os.path.join(instance_path, 'cfgdrive.iso') LOG.debug('Creating config drive at %s', configdrive_iso, instance=instance) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: cdb.make_drive(configdrive_iso) return configdrive_iso
def _setup_spawn_config_drive_mocks(self, use_cdrom): instance_metadata.InstanceMetadata(mox.IgnoreArg(), content=mox.IsA(list), extra_md=mox.IsA(dict)) m = fake.PathUtils.get_instance_dir(mox.IsA(str)) m.AndReturn(self._test_instance_dir) cdb = self._mox.CreateMockAnything() m = configdrive.ConfigDriveBuilder(instance_md=mox.IgnoreArg()) m.AndReturn(cdb) # __enter__ and __exit__ are required by "with" cdb.__enter__().AndReturn(cdb) cdb.make_drive(mox.IsA(str)) cdb.__exit__(None, None, None).AndReturn(None) if not use_cdrom: utils.execute(CONF.hyperv.qemu_img_cmd, 'convert', '-f', 'raw', '-O', 'vpc', mox.IsA(str), mox.IsA(str), attempts=1) fake.PathUtils.remove(mox.IsA(str)) m = vmutils.VMUtils.attach_ide_drive(mox.IsA(str), mox.IsA(str), mox.IsA(int), mox.IsA(int), mox.IsA(str)) m.WithSideEffects(self._add_disk)
def add_instance_metadata(self): inst_md = instance_metadata.InstanceMetadata(self.instance) for (path, value) in inst_md.metadata_for_config_drive(self.injected): self._add_file(path, value) LOG.debug(_('Added %(filepath)s to config drive'), {'filepath': path}, instance=self.instance)
def _create_config_drive(self, instance, injected_files, admin_password): if CONF.config_drive_format != 'iso9660': vmutils.HyperVException( _('Invalid config_drive_format "%s"') % CONF.config_drive_format) LOG.info(_('Using config drive'), instance=instance) extra_md = {} if admin_password and CONF.config_drive_inject_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md) instance_path = self._vmutils.get_instance_path(instance['name']) configdrive_path_iso = os.path.join(instance_path, 'configdrive.iso') LOG.info(_('Creating config drive at %(path)s'), {'path': configdrive_path_iso}, instance=instance) with configdrive.config_drive_helper(instance_md=inst_md) as cdb: try: cdb.make_drive(configdrive_path_iso) except exception.ProcessExecutionError, e: LOG.error(_('Creating config drive failed with error: %s'), e, instance=instance) raise
def _create_cfg_dr_iso(self, instance, injected_files, network_info, admin_pass=None): """Creates an ISO file that contains the injected files. Used for config drive. :param instance: The VM instance from OpenStack. :param injected_files: A list of file paths that will be injected into the ISO. :param network_info: The network_info from the nova spawn method. :param admin_pass: Optional password to inject for the VM. :return iso_path: The path to the ISO :return file_name: The file name for the ISO """ LOG.info("Creating config drive.", instance=instance) extra_md = {} if admin_pass is not None: extra_md['admin_pass'] = admin_pass # Sanitize the vifs for the network config network_info = self._sanitize_network_info(network_info) inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info) if not os.path.exists(_VOPT_TMPDIR): os.mkdir(_VOPT_TMPDIR) file_name = pvm_util.sanitize_file_name_for_api( instance.name, prefix='cfg_', suffix='.iso', max_len=pvm_const.MaxLen.VOPT_NAME) iso_path = os.path.join(_VOPT_TMPDIR, file_name) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: LOG.info("Config drive ISO being built in %s.", iso_path, instance=instance) # There may be an OSError exception when create the config drive. # If so, retry the operation before raising. @retrying.retry( retry_on_exception=lambda exc: isinstance(exc, OSError), stop_max_attempt_number=2) def _make_cfg_drive(iso_path): cdb.make_drive(iso_path) try: _make_cfg_drive(iso_path) return iso_path, file_name except OSError: with excutils.save_and_reraise_exception(logger=LOG): LOG.exception("Config drive ISO could not be built", instance=instance)
def test_InstanceMetadata_uses_passed_network_info(self): network_info = {"a": "b"} self.mox.StubOutWithMock(netutils, "get_injected_network_template") netutils.get_injected_network_template(network_info).AndReturn(False) self.mox.ReplayAll() base.InstanceMetadata(INSTANCES[0], network_info=network_info)
def _create_cfg_dr_iso(self, instance, injected_files, network_info, iso_path, admin_pass=None): """Creates an ISO file that contains the injected files. Used for config drive. :param instance: The VM instance from OpenStack. :param injected_files: A list of file paths that will be injected into the ISO. :param network_info: The network_info from the nova spawn method. :param iso_path: The absolute file path for the new ISO :param admin_pass: Optional password to inject for the VM. """ LOG.info("Creating config drive.", instance=instance) extra_md = {} if admin_pass is not None: extra_md['admin_pass'] = admin_pass # Sanitize the vifs for the network config network_info = self._sanitize_network_info(network_info) inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info) # fix instance uuid to match uuid assigned to VM inst_md.uuid = vm.get_pvm_uuid(instance).lower() with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: LOG.info("Config drive ISO building to path %(iso_path)s.", {'iso_path': iso_path}, instance=instance) # In case, if there's an OSError related failure while # creating config drive, retry make drive operation. def _retry_on_oserror(exc): return isinstance(exc, OSError) @retrying.retry(retry_on_exception=_retry_on_oserror, stop_max_attempt_number=2) def _make_cfg_drive(iso_path): cdb.make_drive(iso_path) try: _make_cfg_drive(iso_path) except OSError: with excutils.save_and_reraise_exception(logger=LOG): # If we get here, that means there's an exception during # second attempt, log the same and fail the deploy # operation. LOG.exception("Config drive ISO could not be built.", instance=instance)
def test_InstanceMetadata_uses_passed_network_info(self): network_info = [] self.mox.StubOutWithMock(netutils, "get_injected_network_template") netutils.get_injected_network_template(network_info).AndReturn(False) self.mox.ReplayAll() base.InstanceMetadata(fake_inst_obj(self.context), network_info=network_info)
def _create_config_drive(self, context, instance, injected_files, admin_password, network_info, rescue=False): if CONF.config_drive_format != 'iso9660': raise exception.ConfigDriveUnsupportedFormat( format=CONF.config_drive_format) LOG.info('Using config drive for instance', instance=instance) extra_md = {} if admin_password and CONF.hyperv.config_drive_inject_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info, request_context=context) configdrive_path_iso = self._pathutils.get_configdrive_path( instance.name, constants.DVD_FORMAT, rescue=rescue) LOG.info('Creating config drive at %(path)s', {'path': configdrive_path_iso}, instance=instance) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: try: cdb.make_drive(configdrive_path_iso) except processutils.ProcessExecutionError as e: with excutils.save_and_reraise_exception(): LOG.error('Creating config drive failed with ' 'error: %s', e, instance=instance) if not CONF.hyperv.config_drive_cdrom: configdrive_path = self._pathutils.get_configdrive_path( instance.name, constants.DISK_FORMAT_VHD, rescue=rescue) utils.execute(CONF.hyperv.qemu_img_cmd, 'convert', '-f', 'raw', '-O', 'vpc', configdrive_path_iso, configdrive_path, attempts=1) self._pathutils.remove(configdrive_path_iso) else: configdrive_path = configdrive_path_iso return configdrive_path
def fake_InstanceMetadata(stubs, inst_data, address=None, sgroups=None): if sgroups is None: sgroups = [{'name': 'default'}] def sg_get(*args, **kwargs): return sgroups stubs.Set(api, 'security_group_get_by_instance', sg_get) return base.InstanceMetadata(inst_data, address=address)
def test_InstanceMetadata_queries_network_API_when_needed(self): network_info_from_api = [] self.mox.StubOutWithMock(netutils, "get_injected_network_template") netutils.get_injected_network_template( network_info_from_api).AndReturn(False) self.mox.ReplayAll() base.InstanceMetadata(fake_inst_obj(self.context))
def _create_cfg_dr_iso(self, instance, injected_files, network_info, admin_pass=None): """Creates an ISO file that contains the injected files. Used for config drive. :param instance: The VM instance from OpenStack. :param injected_files: A list of file paths that will be injected into the ISO. :param network_info: The network_info from the nova spawn method. :param admin_pass: Optional password to inject for the VM. :return iso_path: The path to the ISO :return file_name: The file name for the ISO """ LOG.info(_LI("Creating config drive for instance: %s"), instance.name, instance=instance) extra_md = {} if admin_pass is not None: extra_md['admin_pass'] = admin_pass # Sanitize the vifs for the network config network_info = self._sanitize_network_info(network_info) inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info) # Make sure the path exists. im_path = CONF.powervm.image_meta_local_path if not os.path.exists(im_path): os.mkdir(im_path) file_name = pvm_util.sanitize_file_name_for_api( instance.name, prefix=CFG_DRV_PREFIX, suffix=CFG_DRV_SUFFIX, max_len=pvm_const.MaxLen.VOPT_NAME) iso_path = os.path.join(im_path, file_name) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: LOG.info(_LI("Config drive ISO being built for instance %(inst)s " "building to path %(iso_path)s."), { 'inst': instance.name, 'iso_path': iso_path }, instance=instance) cdb.make_drive(iso_path) return iso_path, file_name
def _create_config_drive(self, instance, injected_files, admin_password): if CONF.config_drive_format != 'iso9660': vmutils.HyperVException( _('Invalid config_drive_format "%s"') % CONF.config_drive_format) LOG.info(_('Using config drive for instance: %s'), instance=instance) extra_md = {} if admin_password and CONF.hyperv.config_drive_inject_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md) instance_path = self._pathutils.get_instance_dir(instance['name']) configdrive_path_iso = os.path.join(instance_path, 'configdrive.iso') LOG.info(_('Creating config drive at %(path)s'), {'path': configdrive_path_iso}, instance=instance) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: try: cdb.make_drive(configdrive_path_iso) except processutils.ProcessExecutionError as e: with excutils.save_and_reraise_exception(): LOG.error(_('Creating config drive failed with error: %s'), e, instance=instance) if not CONF.hyperv.config_drive_cdrom: drive_type = constants.IDE_DISK configdrive_path = os.path.join(instance_path, 'configdrive.vhd') utils.execute(CONF.hyperv.qemu_img_cmd, 'convert', '-f', 'raw', '-O', 'vpc', configdrive_path_iso, configdrive_path, attempts=1) self._pathutils.remove(configdrive_path_iso) else: drive_type = constants.IDE_DVD configdrive_path = configdrive_path_iso self._vmutils.attach_ide_drive(instance['name'], configdrive_path, 1, 0, drive_type)
def fake_InstanceMetadata(stubs, inst_data, address=None, sgroups=None, content=[], extra_md={}, vd_driver=None): if sgroups is None: sgroups = [{'name': 'default'}] def sg_get(*args, **kwargs): return sgroups stubs.Set(api, 'security_group_get_by_instance', sg_get) return base.InstanceMetadata(inst_data, address=address, content=content, extra_md=extra_md, vd_driver=vd_driver)
def _create_config_drive(self, instance, injected_files, admin_password, network_info): if CONF.config_drive_format != 'iso9660': raise vmutils.UnsupportedConfigDriveFormatException( _('Invalid config_drive_format "%s"') % CONF.config_drive_format) LOG.info(_LI('Using config drive for instance'), instance=instance) extra_md = {} if admin_password and CONF.hyperv.config_drive_inject_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info) instance_path = self._pathutils.get_instance_dir(instance.name) configdrive_path_iso = os.path.join(instance_path, 'configdrive.iso') LOG.info(_LI('Creating config drive at %(path)s'), {'path': configdrive_path_iso}, instance=instance) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: try: cdb.make_drive(configdrive_path_iso) except processutils.ProcessExecutionError as e: with excutils.save_and_reraise_exception(): LOG.error(_LE('Creating config drive failed with ' 'error: %s'), e, instance=instance) if not CONF.hyperv.config_drive_cdrom: configdrive_path = os.path.join(instance_path, 'configdrive.vhd') utils.execute(CONF.hyperv.qemu_img_cmd, 'convert', '-f', 'raw', '-O', 'vpc', configdrive_path_iso, configdrive_path, attempts=1) self._pathutils.remove(configdrive_path_iso) else: configdrive_path = configdrive_path_iso return configdrive_path
def _create_cfg_dr_iso(self, instance, injected_files, network_info, iso_path, admin_pass=None): """Creates an ISO file that contains the injected files. Used for config drive. :param instance: The VM instance from OpenStack. :param injected_files: A list of file paths that will be injected into the ISO. :param network_info: The network_info from the nova spawn method. :param iso_path: The absolute file path for the new ISO :param admin_pass: Optional password to inject for the VM. """ LOG.info("Creating config drive.", instance=instance) extra_md = {} if admin_pass is not None: extra_md['admin_pass'] = admin_pass # Sanitize the vifs for the network config network_info = self._sanitize_network_info(network_info) inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: LOG.info("Config drive ISO being built in %s.", iso_path, instance=instance) # There may be an OSError exception when create the config drive. # If so, retry the operation before raising. @retrying.retry( retry_on_exception=lambda exc: isinstance(exc, OSError), stop_max_attempt_number=2) def _make_cfg_drive(iso_path): cdb.make_drive(iso_path) try: _make_cfg_drive(iso_path) except OSError: with excutils.save_and_reraise_exception(logger=LOG): LOG.exception("Config drive ISO could not be built", instance=instance)
def test_InstanceMetadata_queries_network_API_when_needed(self): network_info_from_api = [] self.mox.StubOutWithMock(network_api.API, "get_instance_nw_info") network_api.API.get_instance_nw_info( mox.IgnoreArg(), mox.IgnoreArg()).AndReturn(network_info_from_api) self.mox.StubOutWithMock(netutils, "get_injected_network_template") netutils.get_injected_network_template( network_info_from_api).AndReturn(False) self.mox.ReplayAll() base.InstanceMetadata(INSTANCES[0])
def _create_config_drive(self, instance, injected_files, admin_password): if CONF.config_drive_format != 'iso9660': vmutils.HyperVException( _('Invalid config_drive_format "%s"') % CONF.config_drive_format) LOG.info(_('Using config drive'), instance=instance) extra_md = {} if admin_password and CONF.config_drive_inject_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md) instance_path = self._vmutils.get_instance_path(instance['name']) configdrive_path_iso = os.path.join(instance_path, 'configdrive.iso') LOG.info(_('Creating config drive at %(path)s'), {'path': configdrive_path_iso}, instance=instance) cdb = configdrive.ConfigDriveBuilder(instance_md=inst_md) try: cdb.make_drive(configdrive_path_iso) finally: cdb.cleanup() if not CONF.config_drive_cdrom: drive_type = constants.IDE_DISK configdrive_path = os.path.join(instance_path, 'configdrive.vhd') utils.execute(CONF.qemu_img_cmd, 'convert', '-f', 'raw', '-O', 'vpc', configdrive_path_iso, configdrive_path, attempts=1) os.remove(configdrive_path_iso) else: drive_type = constants.IDE_DVD configdrive_path = configdrive_path_iso self._attach_ide_drive(instance['name'], configdrive_path, 1, 0, drive_type)
def _create_config_drive(self, context, instance_path, instance, injected_files, admin_password, commands, linuxdist): if CONF.config_drive_format not in ['tgz', 'iso9660']: msg = (_("Invalid config drive format %s") % CONF.config_drive_format) raise exception.ZVMConfigDriveError(msg=msg) LOG.debug('Using config drive', instance=instance) extra_md = {} if admin_password: extra_md['admin_pass'] = admin_password udev_settle = linuxdist.get_znetconfig_contents() if udev_settle: if len(commands) == 0: znetconfig = '\n'.join(('#!/bin/bash', udev_settle)) else: znetconfig = '\n'.join(('#!/bin/bash', commands, udev_settle)) znetconfig += '\nrm -rf /tmp/znetconfig.sh\n' # Create a temp file in instance to execute above commands net_cmd_file = [] net_cmd_file.append(('/tmp/znetconfig.sh', znetconfig)) # nosec injected_files.extend(net_cmd_file) # injected_files.extend(('/tmp/znetconfig.sh', znetconfig)) inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, request_context=context) # network_metadata will prevent the hostname of the instance from # being set correctly, so clean the value inst_md.network_metadata = None configdrive_tgz = os.path.join(instance_path, 'cfgdrive.tgz') LOG.debug('Creating config drive at %s' % configdrive_tgz, instance=instance) with zvmconfigdrive.ZVMConfigDriveBuilder(instance_md=inst_md) as cdb: cdb.make_drive(configdrive_tgz) return configdrive_tgz
def test_InstanceMetadata_invoke_metadata_for_config_drive(self): inst = self.instance.obj_clone() inst_md = base.InstanceMetadata(inst) for (path, value) in inst_md.metadata_for_config_drive(): self.assertIsNotNone(path)
def _create_cfg_dr_iso(self, instance, injected_files, network_info, admin_pass=None): """Creates an ISO file that contains the injected files. Used for config drive. :param instance: The VM instance from OpenStack. :param injected_files: A list of file paths that will be injected into the ISO. :param network_info: The network_info from the nova spawn method. :param admin_pass: Optional password to inject for the VM. :return iso_path: The path to the ISO :return file_name: The file name for the ISO """ LOG.info("Creating config drive.", instance=instance) extra_md = {} if admin_pass is not None: extra_md['admin_pass'] = admin_pass # Sanitize the vifs for the network config network_info = self._sanitize_network_info(network_info) inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md, network_info=network_info) # Make sure the path exists. im_path = CONF.powervm.image_meta_local_path if not os.path.exists(im_path): os.mkdir(im_path) file_name = pvm_util.sanitize_file_name_for_api( instance.name, prefix=CFG_DRV_PREFIX, suffix=CFG_DRV_SUFFIX, max_len=pvm_const.MaxLen.VOPT_NAME) iso_path = os.path.join(im_path, file_name) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: LOG.info("Config drive ISO building to path %(iso_path)s.", {'iso_path': iso_path}, instance=instance) # In case, if there's an OSError related failure while # creating config drive, retry make drive operation. def _retry_on_oserror(exc): return isinstance(exc, OSError) @retrying.retry(retry_on_exception=_retry_on_oserror, stop_max_attempt_number=2) def _make_cfg_drive(iso_path): cdb.make_drive(iso_path) try: _make_cfg_drive(iso_path) return iso_path, file_name except OSError: with excutils.save_and_reraise_exception(logger=LOG): # If we get here, that means there's an exception during # second attempt, log the same and fail the deploy # operation. LOG.exception("Config drive ISO could not be built.", instance=instance)
def _add_configdrive(self, context, instance, injected_files, admin_password, network_info): """Create configdrive for the instance.""" if CONF.config_drive_format != 'iso9660': raise exception.ConfigDriveUnsupportedFormat( format=CONF.config_drive_format) container = self.client.containers.get(instance.name) container_id_map = container.config[ 'volatile.last_state.idmap'].split(',') storage_id = container_id_map[2].split(':')[1] extra_md = {} if admin_password: extra_md['admin_pass'] = admin_password inst_md = instance_metadata.InstanceMetadata( instance, content=injected_files, extra_md=extra_md, network_info=network_info, request_context=context) iso_path = os.path.join( common.InstanceAttributes(instance).instance_dir, 'configdrive.iso') with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: try: cdb.make_drive(iso_path) except processutils.ProcessExecutionError as e: with excutils.save_and_reraise_exception(): LOG.error('Creating config drive failed with ' 'error: %s', e, instance=instance) configdrive_dir = os.path.join( nova.conf.CONF.instances_path, instance.name, 'configdrive') if not os.path.exists(configdrive_dir): fileutils.ensure_tree(configdrive_dir) with utils.tempdir() as tmpdir: mounted = False try: _, err = utils.execute('mount', '-o', 'loop,uid=%d,gid=%d' % (os.getuid(), os.getgid()), iso_path, tmpdir, run_as_root=True) mounted = True # Copy and adjust the files from the ISO so that we # dont have the ISO mounted during the life cycle of the # instance and the directory can be removed once the instance # is terminated for ent in os.listdir(tmpdir): shutil.copytree(os.path.join(tmpdir, ent), os.path.join(configdrive_dir, ent)) utils.execute('chmod', '-R', '775', configdrive_dir, run_as_root=True) utils.execute('chown', '-R', storage_id, configdrive_dir, run_as_root=True) finally: if mounted: utils.execute('umount', tmpdir, run_as_root=True) return configdrive_dir
def _add_driver_fields(self, node, instance, image_meta, flavor, admin_pass=None, files=None, network_info=None, preserve_ephemeral=None): icli = client_wrapper.IronicClientWrapper() patch = patcher.create(node).get_deploy_patch(instance, image_meta, flavor, preserve_ephemeral) # Associate the node with an instance patch.append({ 'path': '/instance_uuid', 'op': 'add', 'value': instance['uuid'] }) if configdrive.required_by(instance): LOG.info(_('Using config drive'), instance=instance) extra_md = {} if admin_pass: extra_md['admin_pass'] = admin_pass inst_md = instance_metadata.InstanceMetadata( instance, content=files, extra_md=extra_md, network_info=network_info) fd, configdrive_path = tempfile.mkstemp() os.close(fd) with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: try: cdb.make_drive(configdrive_path) except processutils.ProcessExecutionError as e: with excutils.save_and_reraise_exception(): LOG.error(_('Creating config drive failed ' 'with error: %s'), e, instance=instance) # gzip the configdrive. with open(configdrive_path, "rb") as configdrive_fh: configdrive_payload = base64.b64encode( zlib.compress(configdrive_fh.read())) os.remove(configdrive_path) patch.append({ 'path': '/instance_info/config_drive', 'op': 'add', 'value': configdrive_payload }) try: icli.call('node.update', node.uuid, patch) except ironic_exception.BadRequest: msg = (_("Failed to add deploy parameters on node %(node)s " "when provisioning the instance %(instance)s") % { 'node': node.uuid, 'instance': instance['uuid'] }) LOG.error(msg) raise exception.InstanceDeployFailure(msg)
def test_InstanceMetadata_invoke_metadata_for_config_drive(self): fakes.stub_out_key_pair_funcs(self.stubs) inst = self.instance.obj_clone() inst_md = base.InstanceMetadata(inst) for (path, value) in inst_md.metadata_for_config_drive(): self.assertIsNotNone(path)
def test_InstanceMetadata_gets_network_metadata(self, mock_netutils): network_data = {'links': [], 'networks': [], 'services': []} mock_netutils.return_value = network_data md = base.InstanceMetadata(fake_inst_obj(self.context)) self.assertEqual(network_data, md.network_metadata)
def _add_configdrive(self, instance, injected_files): """Configure the config drive for the container :param instance: nova instance object :param injected_files: instance injected files """ LOG.debug('add_configdrive called for instance', instance=instance) extra_md = {} inst_md = instance_metadata.InstanceMetadata(instance, content=injected_files, extra_md=extra_md) # Create the ISO image so we can inject the contents of the ISO # into the container iso_path = os.path.join(self.instance_dir, 'configdirve.iso') with configdrive.ConfigDriveBuilder(instance_md=inst_md) as cdb: try: cdb.make_drive(iso_path) except Exception as e: with excutils.save_and_reraise_exception(): LOG.error(_LE('Creating config drive failed with error: ' '%s'), e, instance=instance) # Copy the metadata info from the ISO into the container configdrive_dir = \ self.container_dir.get_container_configdrive(instance.name) with utils.tempdir() as tmpdir: mounted = False try: _, err = utils.execute('mount', '-o', 'loop,uid=%d,gid=%d' % (os.getuid(), os.getgid()), iso_path, tmpdir, run_as_root=True) mounted = True # Copy and adjust the files from the ISO so that we # dont have the ISO mounted during the life cycle of the # instance and the directory can be removed once the instance # is terminated for ent in os.listdir(tmpdir): shutil.copytree(os.path.join(tmpdir, ent), os.path.join(configdrive_dir, ent)) utils.execute('chmod', '-R', '775', configdrive_dir, run_as_root=True) utils.execute('chown', '-R', '%s:%s' % (self._uid_map('/etc/subuid').rstrip(), self._uid_map('/etc/subgid').rstrip()), configdrive_dir, run_as_root=True) finally: if mounted: utils.execute('umount', tmpdir, run_as_root=True)