Merge "Fix provisioning failure with ramdisk
deploy interface"
This commit is contained in:
commit
ded9e7ce87
@ -589,6 +589,37 @@ class PXEBoot(base.BootInterface):
|
||||
else:
|
||||
_clean_up_pxe_env(task, images_info)
|
||||
|
||||
def _prepare_instance_pxe_config(self, task, image_info,
|
||||
iscsi_boot=False,
|
||||
ramdisk_boot=False):
|
||||
"""Prepares the config file for PXE boot
|
||||
|
||||
:param task: a task from TaskManager.
|
||||
:param image_info: a dict of values of instance image
|
||||
metadata to set on the configuration file.
|
||||
:param iscsi_boot: if boot is from an iSCSI volume or not.
|
||||
:param ramdisk_boot: if the boot is to a ramdisk configuration.
|
||||
:returns: None
|
||||
"""
|
||||
|
||||
node = task.node
|
||||
dhcp_opts = pxe_utils.dhcp_options_for_instance(task)
|
||||
provider = dhcp_factory.DHCPFactory()
|
||||
provider.update_dhcp(task, dhcp_opts)
|
||||
pxe_config_path = pxe_utils.get_pxe_config_file_path(
|
||||
node.uuid)
|
||||
if not os.path.isfile(pxe_config_path):
|
||||
pxe_options = _build_pxe_config_options(
|
||||
task, image_info, service=ramdisk_boot)
|
||||
pxe_config_template = (
|
||||
deploy_utils.get_pxe_config_template(node))
|
||||
pxe_utils.create_pxe_config(
|
||||
task, pxe_options, pxe_config_template)
|
||||
deploy_utils.switch_pxe_config(
|
||||
pxe_config_path, None,
|
||||
boot_mode_utils.get_boot_mode_for_deploy(node), False,
|
||||
iscsi_boot=iscsi_boot, ramdisk_boot=ramdisk_boot)
|
||||
|
||||
@METRICS.timer('PXEBoot.prepare_instance')
|
||||
def prepare_instance(self, task):
|
||||
"""Prepares the boot of instance.
|
||||
@ -606,40 +637,18 @@ class PXEBoot(base.BootInterface):
|
||||
node = task.node
|
||||
boot_option = deploy_utils.get_boot_option(node)
|
||||
boot_device = None
|
||||
if deploy_utils.is_iscsi_boot(task):
|
||||
dhcp_opts = pxe_utils.dhcp_options_for_instance(task)
|
||||
provider = dhcp_factory.DHCPFactory()
|
||||
provider.update_dhcp(task, dhcp_opts)
|
||||
|
||||
# configure iPXE for iscsi boot
|
||||
pxe_config_path = pxe_utils.get_pxe_config_file_path(
|
||||
task.node.uuid)
|
||||
if not os.path.isfile(pxe_config_path):
|
||||
pxe_options = _build_pxe_config_options(task, {})
|
||||
pxe_config_template = (
|
||||
deploy_utils.get_pxe_config_template(node))
|
||||
pxe_utils.create_pxe_config(
|
||||
task, pxe_options, pxe_config_template)
|
||||
deploy_utils.switch_pxe_config(
|
||||
pxe_config_path, None,
|
||||
boot_mode_utils.get_boot_mode_for_deploy(node), False,
|
||||
iscsi_boot=True)
|
||||
boot_device = boot_devices.PXE
|
||||
|
||||
elif boot_option == "ramdisk":
|
||||
instance_image_info = {}
|
||||
if boot_option == "ramdisk":
|
||||
instance_image_info = _get_instance_image_info(
|
||||
task.node, task.context)
|
||||
_cache_ramdisk_kernel(task.context, task.node,
|
||||
instance_image_info)
|
||||
dhcp_opts = pxe_utils.dhcp_options_for_instance(task)
|
||||
provider = dhcp_factory.DHCPFactory()
|
||||
provider.update_dhcp(task, dhcp_opts)
|
||||
pxe_config_path = pxe_utils.get_pxe_config_file_path(
|
||||
task.node.uuid)
|
||||
deploy_utils.switch_pxe_config(
|
||||
pxe_config_path, None,
|
||||
boot_mode_utils.get_boot_mode_for_deploy(node), False,
|
||||
iscsi_boot=False, ramdisk_boot=True)
|
||||
|
||||
if deploy_utils.is_iscsi_boot(task) or boot_option == "ramdisk":
|
||||
self._prepare_instance_pxe_config(
|
||||
task, instance_image_info,
|
||||
iscsi_boot=deploy_utils.is_iscsi_boot(task),
|
||||
ramdisk_boot=(boot_option == "ramdisk"))
|
||||
boot_device = boot_devices.PXE
|
||||
|
||||
elif boot_option != "local":
|
||||
|
@ -1400,7 +1400,7 @@ class PXEBootTestCase(db_base.DbTestCase):
|
||||
task, mock.ANY, CONF.pxe.pxe_config_template)
|
||||
switch_pxe_config_mock.assert_called_once_with(
|
||||
pxe_config_path, None, boot_modes.LEGACY_BIOS, False,
|
||||
iscsi_boot=True)
|
||||
iscsi_boot=True, ramdisk_boot=False)
|
||||
set_boot_device_mock.assert_called_once_with(task,
|
||||
boot_devices.PXE,
|
||||
persistent=True)
|
||||
@ -1453,6 +1453,59 @@ class PXEBootTestCase(db_base.DbTestCase):
|
||||
clean_up_pxe_config_mock.assert_called_once_with(task)
|
||||
self.assertFalse(set_boot_device_mock.called)
|
||||
|
||||
@mock.patch.object(manager_utils, 'node_set_boot_device', autospec=True)
|
||||
@mock.patch.object(deploy_utils, 'switch_pxe_config', autospec=True)
|
||||
@mock.patch.object(pxe_utils, 'create_pxe_config', autospec=True)
|
||||
@mock.patch.object(dhcp_factory, 'DHCPFactory', autospec=True)
|
||||
@mock.patch.object(pxe, '_cache_ramdisk_kernel', autospec=True)
|
||||
@mock.patch.object(pxe, '_get_instance_image_info', autospec=True)
|
||||
def _test_prepare_instance_ramdisk(
|
||||
self, get_image_info_mock, cache_mock,
|
||||
dhcp_factory_mock, create_pxe_config_mock,
|
||||
switch_pxe_config_mock,
|
||||
set_boot_device_mock, config_file_exits=False):
|
||||
image_info = {'kernel': ['', '/path/to/kernel'],
|
||||
'ramdisk': ['', '/path/to/ramdisk']}
|
||||
get_image_info_mock.return_value = image_info
|
||||
provider_mock = mock.MagicMock()
|
||||
dhcp_factory_mock.return_value = provider_mock
|
||||
self.node.provision_state = states.DEPLOYING
|
||||
get_image_info_mock.return_value = image_info
|
||||
with task_manager.acquire(self.context, self.node.uuid) as task:
|
||||
instance_info = task.node.instance_info
|
||||
instance_info['capabilities'] = {'boot_option': 'ramdisk'}
|
||||
task.node.instance_info = instance_info
|
||||
task.node.save()
|
||||
dhcp_opts = pxe_utils.dhcp_options_for_instance(task)
|
||||
pxe_config_path = pxe_utils.get_pxe_config_file_path(
|
||||
task.node.uuid)
|
||||
task.driver.boot.prepare_instance(task)
|
||||
|
||||
get_image_info_mock.assert_called_once_with(
|
||||
task.node, task.context)
|
||||
cache_mock.assert_called_once_with(
|
||||
task.context, task.node, image_info)
|
||||
provider_mock.update_dhcp.assert_called_once_with(task, dhcp_opts)
|
||||
if config_file_exits:
|
||||
self.assertFalse(create_pxe_config_mock.called)
|
||||
else:
|
||||
create_pxe_config_mock.assert_called_once_with(
|
||||
task, mock.ANY, CONF.pxe.pxe_config_template)
|
||||
switch_pxe_config_mock.assert_called_once_with(
|
||||
pxe_config_path, None,
|
||||
'bios', False, iscsi_boot=False, ramdisk_boot=True)
|
||||
set_boot_device_mock.assert_called_once_with(task,
|
||||
boot_devices.PXE,
|
||||
persistent=True)
|
||||
|
||||
@mock.patch.object(os.path, 'isfile', lambda path: True)
|
||||
def test_prepare_instance_ramdisk_pxe_conf_missing(self):
|
||||
self._test_prepare_instance_ramdisk(config_file_exits=True)
|
||||
|
||||
@mock.patch.object(os.path, 'isfile', lambda path: False)
|
||||
def test_prepare_instance_ramdisk_pxe_conf_exists(self):
|
||||
self._test_prepare_instance_ramdisk(config_file_exits=False)
|
||||
|
||||
@mock.patch.object(pxe, '_clean_up_pxe_env', autospec=True)
|
||||
@mock.patch.object(pxe, '_get_instance_image_info', autospec=True)
|
||||
def test_clean_up_instance(self, get_image_info_mock,
|
||||
|
@ -0,0 +1,7 @@
|
||||
---
|
||||
fixes:
|
||||
- |
|
||||
Fixes an issue wherein provisioning fails if ironic node is configured
|
||||
with ``ramdisk`` deploy interface.
|
||||
See `bug 2003532 <https://storyboard.openstack.org/#!/story/2003532>`_ for
|
||||
more details.
|
Loading…
x
Reference in New Issue
Block a user