From 85c0dd4929d74db87bce9017a19ea471f1f11fbd Mon Sep 17 00:00:00 2001 From: Steve Baker Date: Fri, 19 Nov 2021 14:56:13 +1300 Subject: [PATCH] Use driver_internal_info methods for driver utils This change switches driver utility and base classes to using set_driver_internal_info, del_driver_internal_info, timestamp_driver_internal_info node methods for modifying driver_internal_info. Specific drivers with switch over later in this series. Change-Id: I4bdfe447cb4636f3f9efad3f2cb17ebddcacce4b --- ironic/drivers/modules/agent_base.py | 53 ++++++--------- ironic/drivers/modules/boot_mode_utils.py | 8 +-- ironic/drivers/modules/deploy_utils.py | 81 ++++++++++++----------- ironic/drivers/utils.py | 17 ++--- 4 files changed, 72 insertions(+), 87 deletions(-) diff --git a/ironic/drivers/modules/agent_base.py b/ironic/drivers/modules/agent_base.py index 8f5a4412a6..e4a48e0fd7 100644 --- a/ironic/drivers/modules/agent_base.py +++ b/ironic/drivers/modules/agent_base.py @@ -21,7 +21,6 @@ import collections from ironic_lib import metrics_utils from oslo_log import log from oslo_utils import strutils -from oslo_utils import timeutils import tenacity from ironic.common import boot_devices @@ -209,15 +208,15 @@ def _post_step_reboot(task, step_type): return # Signify that we've rebooted - driver_internal_info = task.node.driver_internal_info - field = ('cleaning_reboot' if step_type == 'clean' - else 'deployment_reboot') - driver_internal_info[field] = True - if not driver_internal_info.get('agent_secret_token_pregenerated', False): + if step_type == 'clean': + task.node.set_driver_internal_info('cleaning_reboot', True) + else: + task.node.set_driver_internal_info('deployment_reboot', True) + if not task.node.driver_internal_info.get( + 'agent_secret_token_pregenerated', False): # Wipes out the existing recorded token because the machine will # need to re-establish the token. - driver_internal_info.pop('agent_secret_token', None) - task.node.driver_internal_info = driver_internal_info + task.node.del_driver_internal_info('agent_secret_token') task.node.save() @@ -591,22 +590,17 @@ class HeartbeatMixin(object): node = task.node LOG.debug('Heartbeat from node %s in state %s (target state %s)', node.uuid, node.provision_state, node.target_provision_state) - driver_internal_info = node.driver_internal_info - driver_internal_info['agent_url'] = callback_url - driver_internal_info['agent_version'] = agent_version - # Record the last heartbeat event time in UTC, so we can make - # decisions about it later. Can be decoded to datetime object with: - # datetime.datetime.strptime(var, "%Y-%m-%d %H:%M:%S.%f") - driver_internal_info['agent_last_heartbeat'] = str( - timeutils.utcnow().isoformat()) + node.set_driver_internal_info('agent_url', callback_url) + node.set_driver_internal_info('agent_version', agent_version) + # Record the last heartbeat event time + node.timestamp_driver_internal_info('agent_last_heartbeat') if agent_verify_ca: - driver_internal_info['agent_verify_ca'] = agent_verify_ca + node.set_driver_internal_info('agent_verify_ca', agent_verify_ca) if agent_status: - driver_internal_info['agent_status'] = agent_status + node.set_driver_internal_info('agent_status', agent_status) if agent_status_message: - driver_internal_info['agent_status_message'] = \ - agent_status_message - node.driver_internal_info = driver_internal_info + node.set_driver_internal_info('agent_status_message', + agent_status_message) node.save() if node.provision_state in _HEARTBEAT_RECORD_ONLY: @@ -840,13 +834,12 @@ class AgentBaseMixin(object): steps[step['interface']].append(step) # Save hardware manager version, steps, and date - info = node.driver_internal_info - info['hardware_manager_version'] = agent_result[ - 'hardware_manager_version'] - info['agent_cached_%s_steps' % step_type] = dict(steps) - info['agent_cached_%s_steps_refreshed' % step_type] = str( - timeutils.utcnow()) - node.driver_internal_info = info + node.set_driver_internal_info('hardware_manager_version', + agent_result['hardware_manager_version']) + node.set_driver_internal_info('agent_cached_%s_steps' % step_type, + dict(steps)) + node.timestamp_driver_internal_info( + 'agent_cached_%s_steps_refreshed' % step_type) node.save() LOG.debug('Refreshed agent %(type)s step cache for node %(node)s: ' '%(steps)s', {'node': node.uuid, 'steps': steps, @@ -896,9 +889,7 @@ class AgentBaseMixin(object): 'continuing from current step %(step)s.', {'node': node.uuid, 'step': node.clean_step}) - driver_internal_info = node.driver_internal_info - driver_internal_info['skip_current_clean_step'] = False - node.driver_internal_info = driver_internal_info + node.set_driver_internal_info('skip_current_clean_step', False) node.save() else: # Restart the process, agent must have rebooted to new version diff --git a/ironic/drivers/modules/boot_mode_utils.py b/ironic/drivers/modules/boot_mode_utils.py index c6a08d9130..737aca24c5 100644 --- a/ironic/drivers/modules/boot_mode_utils.py +++ b/ironic/drivers/modules/boot_mode_utils.py @@ -110,10 +110,8 @@ def sync_boot_mode(task): # the new boot mode may be set in 'driver_internal_info/deploy_boot_mode' if not ironic_boot_mode and not bm_boot_mode: - driver_internal_info = node.driver_internal_info default_boot_mode = CONF.deploy.default_boot_mode - driver_internal_info['deploy_boot_mode'] = default_boot_mode - node.driver_internal_info = driver_internal_info + node.set_driver_internal_info('deploy_boot_mode', default_boot_mode) node.save() LOG.debug("Ironic node %(uuid)s boot mode will be set to default " @@ -123,9 +121,7 @@ def sync_boot_mode(task): _set_boot_mode_on_bm(task, default_boot_mode) elif not ironic_boot_mode and bm_boot_mode: - driver_internal_info = node.driver_internal_info - driver_internal_info['deploy_boot_mode'] = bm_boot_mode - node.driver_internal_info = driver_internal_info + node.set_driver_internal_info('deploy_boot_mode', bm_boot_mode) node.save() LOG.debug("Ironic node %(uuid)s boot mode is set to boot mode " diff --git a/ironic/drivers/modules/deploy_utils.py b/ironic/drivers/modules/deploy_utils.py index a22b4ff2dd..f46250e2af 100644 --- a/ironic/drivers/modules/deploy_utils.py +++ b/ironic/drivers/modules/deploy_utils.py @@ -306,30 +306,36 @@ def agent_add_clean_params(task): :param task: a TaskManager instance. """ - info = task.node.driver_internal_info random_iterations = CONF.deploy.shred_random_overwrite_iterations - info['agent_erase_devices_iterations'] = random_iterations + node = task.node + node.set_driver_internal_info('agent_erase_devices_iterations', + random_iterations) zeroize = CONF.deploy.shred_final_overwrite_with_zeros - info['agent_erase_devices_zeroize'] = zeroize + node.set_driver_internal_info('agent_erase_devices_zeroize', zeroize) erase_fallback = CONF.deploy.continue_if_disk_secure_erase_fails - info['agent_continue_if_secure_erase_failed'] = erase_fallback + node.set_driver_internal_info('agent_continue_if_secure_erase_failed', + erase_fallback) # NOTE(janders) ``agent_continue_if_ata_erase_failed`` is deprecated and # will be removed in the "Y" cycle. The replacement option # ``agent_continue_if_secure_erase_failed`` is used to control shred # fallback for both ATA Secure Erase and NVMe Secure Erase. # The ``agent_continue_if_ata_erase_failed`` line can # be deleted along with this comment when support for it is fully removed. - info['agent_continue_if_ata_erase_failed'] = erase_fallback + node.set_driver_internal_info('agent_continue_if_ata_erase_failed', + erase_fallback) nvme_secure_erase = CONF.deploy.enable_nvme_secure_erase - info['agent_enable_nvme_secure_erase'] = nvme_secure_erase + node.set_driver_internal_info('agent_enable_nvme_secure_erase', + nvme_secure_erase) secure_erase = CONF.deploy.enable_ata_secure_erase - info['agent_enable_ata_secure_erase'] = secure_erase - info['disk_erasure_concurrency'] = CONF.deploy.disk_erasure_concurrency - info['agent_erase_skip_read_only'] = CONF.deploy.erase_skip_read_only + node.set_driver_internal_info('agent_enable_ata_secure_erase', + secure_erase) + node.set_driver_internal_info('disk_erasure_concurrency', + CONF.deploy.disk_erasure_concurrency) + node.set_driver_internal_info('agent_erase_skip_read_only', + CONF.deploy.erase_skip_read_only) - task.node.driver_internal_info = info - task.node.save() + node.save() def try_set_boot_device(task, device, persistent=True): @@ -922,13 +928,12 @@ def _check_disk_layout_unchanged(node, i_info): """ # If a node has been deployed to, this is the instance information # used for that deployment. - driver_internal_info = node.driver_internal_info - if 'instance' not in driver_internal_info: + if 'instance' not in node.driver_internal_info: return error_msg = '' for param in DISK_LAYOUT_PARAMS: - param_value = int(driver_internal_info['instance'][param]) + param_value = int(node.driver_internal_info['instance'][param]) if param_value != int(i_info[param]): error_msg += (_(' Deployed value of %(param)s was %(param_value)s ' 'but requested value is %(request_value)s.') % @@ -1271,19 +1276,17 @@ def populate_storage_driver_internal_info(task): boot_capability = ("%s_volume_boot" % vol_type) deploy_capability = ("%s_volume_deploy" % vol_type) vol_uuid = boot_volume['uuid'] - driver_internal_info = node.driver_internal_info if check_interface_capability(task.driver.boot, boot_capability): - driver_internal_info['boot_from_volume'] = vol_uuid + node.set_driver_internal_info('boot_from_volume', vol_uuid) # NOTE(TheJulia): This would be a convenient place to check # if we need to know about deploying the volume. if (check_interface_capability(task.driver.deploy, deploy_capability) and task.driver.storage.should_write_image(task)): - driver_internal_info['boot_from_volume_deploy'] = vol_uuid + node.set_driver_internal_info('boot_from_volume_deploy', vol_uuid) # NOTE(TheJulia): This is also a useful place to include a # root device hint since we should/might/be able to obtain # and supply that information to IPA if it needs to write # the image to the volume. - node.driver_internal_info = driver_internal_info node.save() @@ -1305,10 +1308,8 @@ def tear_down_storage_configuration(task): {'target': volume.uuid, 'node': task.node.uuid}) node = task.node - driver_internal_info = node.driver_internal_info - driver_internal_info.pop('boot_from_volume', None) - driver_internal_info.pop('boot_from_volume_deploy', None) - node.driver_internal_info = driver_internal_info + node.del_driver_internal_info('boot_from_volume') + node.del_driver_internal_info('boot_from_volume_deploy') node.save() @@ -1346,7 +1347,7 @@ def get_async_step_return_state(node): return states.CLEANWAIT if node.clean_step else states.DEPLOYWAIT -def _check_agent_token_prior_to_agent_reboot(driver_internal_info): +def _check_agent_token_prior_to_agent_reboot(node): """Removes the agent token if it was not pregenerated. Removal of the agent token in cases where it is not pregenerated @@ -1357,11 +1358,11 @@ def _check_agent_token_prior_to_agent_reboot(driver_internal_info): already included in the payload and must be generated again upon lookup. - :param driver_internal_info: The driver_interal_info dict object - from a Node object. + :param node: The Node object. """ - if not driver_internal_info.get('agent_secret_token_pregenerated', False): - driver_internal_info.pop('agent_secret_token', None) + if not node.driver_internal_info.get('agent_secret_token_pregenerated', + False): + node.del_driver_internal_info('agent_secret_token') def set_async_step_flags(node, reboot=None, skip_current_step=None, @@ -1383,25 +1384,25 @@ def set_async_step_flags(node, reboot=None, skip_current_step=None, corresponding polling flag is not set in the node's driver_internal_info. """ - info = node.driver_internal_info - cleaning = {'reboot': 'cleaning_reboot', - 'skip': 'skip_current_clean_step', - 'polling': 'cleaning_polling'} - deployment = {'reboot': 'deployment_reboot', - 'skip': 'skip_current_deploy_step', - 'polling': 'deployment_polling'} - fields = cleaning if node.clean_step else deployment + if node.clean_step: + reboot_field = 'cleaning_reboot' + skip_field = 'skip_current_clean_step' + polling_field = 'cleaning_polling' + else: + reboot_field = 'deployment_reboot' + skip_field = 'skip_current_deploy_step' + polling_field = 'deployment_polling' + if reboot is not None: - info[fields['reboot']] = reboot + node.set_driver_internal_info(reboot_field, reboot) if reboot: # If rebooting, we must ensure that we check and remove # an agent token if necessary. - _check_agent_token_prior_to_agent_reboot(info) + _check_agent_token_prior_to_agent_reboot(node) if skip_current_step is not None: - info[fields['skip']] = skip_current_step + node.set_driver_internal_info(skip_field, skip_current_step) if polling is not None: - info[fields['polling']] = polling - node.driver_internal_info = info + node.set_driver_internal_info(polling_field, polling) node.save() diff --git a/ironic/drivers/utils.py b/ironic/drivers/utils.py index 55b18542ba..b90660b596 100644 --- a/ironic/drivers/utils.py +++ b/ironic/drivers/utils.py @@ -194,13 +194,12 @@ def ensure_next_boot_device(task, driver_info): """ ifbd = driver_info.get('force_boot_device', False) if strutils.bool_from_string(ifbd): - driver_internal_info = task.node.driver_internal_info - if driver_internal_info.get('is_next_boot_persistent') is False: - driver_internal_info.pop('is_next_boot_persistent', None) - task.node.driver_internal_info = driver_internal_info + info = task.node.driver_internal_info + if info.get('is_next_boot_persistent') is False: + task.node.del_driver_internal_info('is_next_boot_persistent') task.node.save() else: - boot_device = driver_internal_info.get('persistent_boot_device') + boot_device = info.get('persistent_boot_device') if boot_device: utils.node_set_boot_device(task, boot_device) @@ -218,14 +217,12 @@ def force_persistent_boot(task, device, persistent): """ node = task.node - driver_internal_info = node.driver_internal_info if persistent: - driver_internal_info.pop('is_next_boot_persistent', None) - driver_internal_info['persistent_boot_device'] = device + node.del_driver_internal_info('is_next_boot_persistent') + node.set_driver_internal_info('persistent_boot_device', device) else: - driver_internal_info['is_next_boot_persistent'] = False + node.set_driver_internal_info('is_next_boot_persistent', False) - node.driver_internal_info = driver_internal_info node.save()