def validate(self, task): """Validates the driver information needed by the iBMC driver. :param task: A TaskManager instance containing the node to act on. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) """ utils.parse_driver_info(task.node)
def test_parse_driver_info_valid_string_value_verify_ca(self): for value in ('0', 'f', 'false', 'off', 'n', 'no'): self.node.driver_info['ibmc_verify_ca'] = value response = utils.parse_driver_info(self.node) parsed_driver_info = copy.deepcopy(self.parsed_driver_info) parsed_driver_info['verify_ca'] = False self.assertEqual(parsed_driver_info, response) for value in ('1', 't', 'true', 'on', 'y', 'yes'): self.node.driver_info['ibmc_verify_ca'] = value response = utils.parse_driver_info(self.node) self.assertEqual(self.parsed_driver_info, response)
def validate(self, task, method=None, **kwargs): """Validate vendor-specific actions. If invalid, raises an exception; otherwise returns None. :param task: A task from TaskManager. :param method: Method to be validated :param kwargs: Info for action. :raises: UnsupportedDriverExtension if 'method' can not be mapped to the supported interfaces. :raises: InvalidParameterValue if kwargs does not contain 'method'. :raises: MissingParameterValue """ utils.parse_driver_info(task.node)
def reboot(self, task, timeout=None): """Perform a hard reboot of the task's node. :param task: A TaskManager instance containing the node to act on. :param timeout: Time to wait for the node to become powered on. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue if a required parameter is missing. :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() current_power_state = ( mappings.GET_POWER_STATE_MAP.get(system.power_state) ) if current_power_state == states.POWER_ON: conn.system.reset( mappings.SET_POWER_STATE_MAP.get(states.REBOOT)) else: conn.system.reset( mappings.SET_POWER_STATE_MAP.get(states.POWER_ON)) cond_utils.node_wait_for_power_state(task, states.POWER_ON, timeout=timeout)
def get_boot_device(self, task): """Get the current boot device for a node. :param task: A task from TaskManager. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information :returns: a dictionary containing: :boot_device: the boot device, one of :mod:`ironic.common.boot_devices` or None if it is unknown. :persistent: Boolean value or None, True if the boot device persists, False otherwise. None if it's disabled. """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() boot_source_override = system.boot_source_override boot_device = boot_source_override.target enabled = boot_source_override.enabled return { 'boot_device': mappings.GET_BOOT_DEVICE_MAP.get(boot_device), 'persistent': mappings.GET_BOOT_DEVICE_PERSISTENT_MAP.get(enabled) }
def reboot(self, task, timeout=None): """Perform a hard reboot of the task's node. :param task: A TaskManager instance containing the node to act on. :param timeout: Time to wait for the node to become powered on. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue if a required parameter is missing. :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() current_power_state = (mappings.GET_POWER_STATE_MAP.get( system.power_state)) if current_power_state == states.POWER_ON: conn.system.reset( mappings.SET_POWER_STATE_MAP.get(states.REBOOT)) else: conn.system.reset( mappings.SET_POWER_STATE_MAP.get(states.POWER_ON)) cond_utils.node_wait_for_power_state(task, states.POWER_ON, timeout=timeout)
def test_parse_driver_info_valid_capath(self, mock_isfile): mock_isfile.return_value = True fake_path = '/path/to/a/valid/CA.pem' self.node.driver_info['ibmc_verify_ca'] = fake_path self.parsed_driver_info['verify_ca'] = fake_path response = utils.parse_driver_info(self.node) self.assertEqual(self.parsed_driver_info, response) mock_isfile.assert_called_once_with(fake_path)
def setUp(self): super(IBMCTestCase, self).setUp() self.driver_info = db_utils.get_test_ibmc_info() self.config(enabled_hardware_types=['ibmc'], enabled_power_interfaces=['ibmc'], enabled_management_interfaces=['ibmc'], enabled_vendor_interfaces=['ibmc']) self.node = obj_utils.create_test_node( self.context, driver='ibmc', driver_info=self.driver_info) self.ibmc = utils.parse_driver_info(self.node)
def setUp(self): super(IBMCTestCase, self).setUp() self.driver_info = db_utils.get_test_ibmc_info() self.config(enabled_hardware_types=['ibmc'], enabled_power_interfaces=['ibmc'], enabled_management_interfaces=['ibmc'], enabled_vendor_interfaces=['ibmc']) self.node = obj_utils.create_test_node(self.context, driver='ibmc', driver_info=self.driver_info) self.ibmc = utils.parse_driver_info(self.node)
def _delete_raid_configuration(self, task): """Delete the RAID configuration through `python-ibmcclient` lib. :param task: a TaskManager instance containing the node to act on. """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: # NOTE(qianbiao.ng): To reduce review workload, we should keep all # delete logic in python-ibmcclient. And delete raid configuration # logic should be synchronized. if async required, do it in # python-ibmcclient. conn.system.storage.delete_all_raid_configuration()
def get_power_state(self, task): """Get the current power state of the task's node. :param task: A TaskManager instance containing the node to act on. :returns: A power state. One of :mod:`ironic.common.states`. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() return mappings.GET_POWER_STATE_MAP.get(system.power_state)
def inject_nmi(self, task): """Inject NMI, Non Maskable Interrupt. Inject NMI (Non Maskable Interrupt) for a node immediately. :param task: A TaskManager instance containing the node to act on. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: conn.system.reset(constants.RESET_NMI)
def get_raid_controller_list(self, task, **kwargs): """List RAID controllers summary info of the node. :param task: A TaskManager instance containing the node to act on. :param kwargs: Not used. :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information :returns: A list of dictionaries, every dictionary represents a RAID controller summary of node. """ driver_info = utils.parse_driver_info(task.node) with ibmc_client.connect(**driver_info) as conn: controllers = conn.system.storage.list() summaries = [ctrl.summary() for ctrl in controllers] return summaries
def _create_raid_configuration(self, task, logical_disks): """Create the RAID configuration through `python-ibmcclient` lib. :param task: a TaskManager instance containing the node to act on. :param logical_disks: a list of JSON dictionaries which represents the logical disks to be created. The JSON dictionary should match the (ironic.drivers.raid_config_schema.json) scheme. """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: # NOTE(qianbiao.ng): To reduce review workload, we should keep all # apply logic in python-ibmcclient. And apply raid configuration # logic should be synchronized. if async required, do it in # python-ibmcclient. conn.system.storage.apply_raid_configuration(logical_disks)
def boot_up_seq(self, task, **kwargs): """List boot type order of the node. :param task: A TaskManager instance containing the node to act on. :param kwargs: Not used. :raises: InvalidParameterValue if kwargs does not contain 'method'. :raises: MissingParameterValue :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information :returns: A dictionary, containing node boot up sequence, in ascending order. """ driver_info = utils.parse_driver_info(task.node) with ibmc_client.connect(**driver_info) as conn: system = conn.system.get() boot_sequence = system.boot_sequence return {'boot_up_sequence': boot_sequence}
def get_supported_boot_devices(self, task): """Get a list of the supported boot devices. :param task: a task from TaskManager. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information :returns: A list with the supported boot devices defined in :mod:`ironic.common.boot_devices`. """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() boot_source_override = system.boot_source_override return list(map(mappings.GET_BOOT_DEVICE_MAP.get, boot_source_override.supported_boot_devices))
def get_supported_boot_devices(self, task): """Get a list of the supported boot devices. :param task: a task from TaskManager. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information :returns: A list with the supported boot devices defined in :mod:`ironic.common.boot_devices`. """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() boot_source_override = system.boot_source_override return list( map(mappings.GET_BOOT_DEVICE_MAP.get, boot_source_override.supported_boot_devices))
def set_power_state(self, task, power_state, timeout=None): """Set the power state of the task's node. :param task: A TaskManager instance containing the node to act on. :param power_state: Any power state from :mod:`ironic.common.states`. :param timeout: Time to wait for the node to reach the requested state. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue if a required parameter is missing. :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: reset_type = mappings.SET_POWER_STATE_MAP.get(power_state) conn.system.reset(reset_type) target_state = EXPECT_POWER_STATE_MAP.get(power_state, power_state) cond_utils.node_wait_for_power_state(task, target_state, timeout=timeout)
def set_boot_device(self, task, device, persistent=False): """Set the boot device for a node. :param task: A task from TaskManager. :param device: The boot device, one of :mod:`ironic.common.boot_device`. :param persistent: Boolean value. True if the boot device will persist to all future boots, False if not. Default: False. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: boot_device = mappings.SET_BOOT_DEVICE_MAP[device] enabled = mappings.SET_BOOT_DEVICE_PERSISTENT_MAP[persistent] conn.system.set_boot_source(boot_device, enabled=enabled)
def get_boot_mode(self, task): """Get the current boot mode for a node. Provides the current boot mode of the node. :param task: A task from TaskManager. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information :returns: The boot mode, one of :mod:`ironic.common.boot_mode` or None if it is unknown. """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() boot_source_override = system.boot_source_override boot_mode = boot_source_override.mode return mappings.GET_BOOT_MODE_MAP.get(boot_mode)
def set_boot_mode(self, task, mode): """Set the boot mode for a node. Set the boot mode to use on next reboot of the node. :param task: A task from TaskManager. :param mode: The boot mode, one of :mod:`ironic.common.boot_modes`. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() boot_source_override = system.boot_source_override boot_device = boot_source_override.target boot_override = boot_source_override.enabled # Copied from redfish driver # TODO(Qianbiao.NG) what if boot device is "NONE"? if not boot_device: error_msg = (_('Cannot change boot mode on node %(node)s ' 'because its boot device is not set.') % { 'node': task.node.uuid }) LOG.error(error_msg) raise exception.IBMCError(error_msg) # TODO(Qianbiao.NG) what if boot override is "disabled"? if not boot_override: i18n = _('Cannot change boot mode on node %(node)s ' 'because its boot source override is not set.') error_msg = i18n % {'node': task.node.uuid} LOG.error(error_msg) raise exception.IBMCError(error_msg) boot_mode = mappings.SET_BOOT_MODE_MAP[mode] conn.system.set_boot_source(boot_device, enabled=boot_override, mode=boot_mode)
def set_boot_mode(self, task, mode): """Set the boot mode for a node. Set the boot mode to use on next reboot of the node. :param task: A task from TaskManager. :param mode: The boot mode, one of :mod:`ironic.common.boot_modes`. :raises: InvalidParameterValue on malformed parameter(s) :raises: MissingParameterValue on missing parameter(s) :raises: IBMCConnectionError when it fails to connect to iBMC :raises: IBMCError when iBMC responses an error information """ ibmc = utils.parse_driver_info(task.node) with ibmc_client.connect(**ibmc) as conn: system = conn.system.get() boot_source_override = system.boot_source_override boot_device = boot_source_override.target boot_override = boot_source_override.enabled # Copied from redfish driver # TODO(Qianbiao.NG) what if boot device is "NONE"? if not boot_device: error_msg = (_('Cannot change boot mode on node %(node)s ' 'because its boot device is not set.') % {'node': task.node.uuid}) LOG.error(error_msg) raise exception.IBMCError(error_msg) # TODO(Qianbiao.NG) what if boot override is "disabled"? if not boot_override: i18n = _('Cannot change boot mode on node %(node)s ' 'because its boot source override is not set.') error_msg = i18n % {'node': task.node.uuid} LOG.error(error_msg) raise exception.IBMCError(error_msg) boot_mode = mappings.SET_BOOT_MODE_MAP[mode] conn.system.set_boot_source(boot_device, enabled=boot_override, mode=boot_mode)
def get_ibmc_system(_task): driver_info = utils.parse_driver_info(_task.node) with ibmc_client.connect(**driver_info) as _conn: return _conn.system.get()
def test_parse_driver_info(self): response = utils.parse_driver_info(self.node) self.assertEqual(self.parsed_driver_info, response)
def test_parse_driver_info_default_scheme(self): self.node.driver_info['ibmc_address'] = 'example.com' response = utils.parse_driver_info(self.node) self.assertEqual(self.parsed_driver_info, response)
def test_parse_driver_info_default_scheme_with_port(self): self.node.driver_info['ibmc_address'] = 'example.com:42' self.parsed_driver_info['address'] = 'https://example.com:42' response = utils.parse_driver_info(self.node) self.assertEqual(self.parsed_driver_info, response)