Merge "Introduce default kernel/ramdisks by arch"
This commit is contained in:
commit
8be7efdeab
@ -83,7 +83,8 @@ Deploy ramdisk images
|
||||
--disk-format aki --container-format aki \
|
||||
--file ironic-python-agent.vmlinuz
|
||||
|
||||
Store the image UUID obtained from the above step as ``DEPLOY_VMLINUZ_UUID``.
|
||||
Store the image UUID obtained from the above step as ``DEPLOY_VMLINUZ_UUID``
|
||||
(or a different name when using the parameter specified by node architecture).
|
||||
|
||||
.. code-block:: console
|
||||
|
||||
@ -91,14 +92,29 @@ Deploy ramdisk images
|
||||
--disk-format ari --container-format ari \
|
||||
--file ironic-python-agent.initramfs
|
||||
|
||||
Store the image UUID obtained from the above step as ``DEPLOY_INITRD_UUID``.
|
||||
Store the image UUID obtained from the above step as ``DEPLOY_INITRD_UUID``
|
||||
(or a different name when using the parameter specified by node architecture).
|
||||
|
||||
#. Configure the Bare Metal service to use the produced images. It can be done
|
||||
per node as described in :doc:`enrollment` or globally in the configuration
|
||||
file:
|
||||
per node as described in :doc:`enrollment` or in the configuration
|
||||
file either using a dictionary to specify them by architecture as follows:
|
||||
|
||||
.. code-block:: ini
|
||||
|
||||
[conductor]
|
||||
deploy_kernel_by_arch = {'x86_64': <insert DEPLOY_VMLINUZ_X86_64_UUID>,
|
||||
'aarch64': <insert DEPLOY_VMLINUZ_AARCH64_UUID>}
|
||||
deploy_ramdisk_by_arch = {'x86_64': <insert DEPLOY_INITRD_X86_64_UUID>,
|
||||
'aarch64': <insert DEPLOY_INITRD_AARCH64_UUID>}
|
||||
|
||||
or globally using the general configuration parameters:
|
||||
|
||||
.. code-block:: ini
|
||||
|
||||
[conductor]
|
||||
deploy_kernel = <insert DEPLOY_VMLINUZ_UUID>
|
||||
deploy_ramdisk = <insert DEPLOY_INITRD_UUID>
|
||||
|
||||
In the case when both general parameters and parameters specified by
|
||||
architecture are defined, the parameters specified by architecture take
|
||||
priority.
|
||||
|
@ -205,20 +205,56 @@ opts = [
|
||||
'endpoint via multicast DNS.')),
|
||||
cfg.StrOpt('deploy_kernel',
|
||||
mutable=True,
|
||||
help=_('Glance ID, http:// or file:// URL of the kernel of '
|
||||
'the default deploy image.')),
|
||||
deprecated_for_removal=True,
|
||||
deprecated_reason=_('Replaced by deploy_kernel_by_arch which '
|
||||
'provides more configuration options.'),
|
||||
help=_('DEPRECATED: Glance ID, http:// or file:// URL of the '
|
||||
'kernel of the default deploy image.')),
|
||||
cfg.StrOpt('deploy_ramdisk',
|
||||
mutable=True,
|
||||
help=_('Glance ID, http:// or file:// URL of the initramfs of '
|
||||
'the default deploy image.')),
|
||||
deprecated_for_removal=True,
|
||||
deprecated_reason=_('Replaced by deploy_ramdisk_by_arch which '
|
||||
'provides more configuration options.'),
|
||||
help=_('DEPRECATED: Glance ID, http:// or file:// URL of the '
|
||||
'initramfs of the default deploy image.')),
|
||||
cfg.DictOpt('deploy_kernel_by_arch',
|
||||
default={},
|
||||
mutable=True,
|
||||
help=_('A dictionary of key-value pairs of each architecture '
|
||||
'with the Glance ID, http:// or file:// URL of the '
|
||||
'kernel of the default deploy image.')),
|
||||
cfg.DictOpt('deploy_ramdisk_by_arch',
|
||||
default={},
|
||||
mutable=True,
|
||||
help=_('A dictionary of key-value pairs of each architecture '
|
||||
'with the Glance ID, http:// or file:// URL of the '
|
||||
'initramfs of the default deploy image.')),
|
||||
cfg.StrOpt('rescue_kernel',
|
||||
mutable=True,
|
||||
help=_('Glance ID, http:// or file:// URL of the kernel of '
|
||||
'the default rescue image.')),
|
||||
deprecated_for_removal=True,
|
||||
deprecated_reason=_('Replaced by rescue_kernel_by_arch which '
|
||||
'provides more configuration options.'),
|
||||
help=_('DEPRECATED: Glance ID, http:// or file:// URL of the '
|
||||
'kernel of the default rescue image.')),
|
||||
cfg.StrOpt('rescue_ramdisk',
|
||||
mutable=True,
|
||||
help=_('Glance ID, http:// or file:// URL of the initramfs of '
|
||||
'the default rescue image.')),
|
||||
deprecated_for_removal=True,
|
||||
deprecated_reason=_('Replaced by rescue_ramdisk_by_arch which '
|
||||
'provides more configuration options.'),
|
||||
help=_('DEPRECATED: Glance ID, http:// or file:// URL of the '
|
||||
'initramfs of the default rescue image.')),
|
||||
cfg.DictOpt('rescue_kernel_by_arch',
|
||||
default={},
|
||||
mutable=True,
|
||||
help=_('A dictionary of key-value pairs of each architecture '
|
||||
'with the Glance ID, http:// or file:// URL of the '
|
||||
'kernel of the default rescue image.')),
|
||||
cfg.DictOpt('rescue_ramdisk_by_arch',
|
||||
default={},
|
||||
mutable=True,
|
||||
help=_('A dictionary of key-value pairs of each architecture '
|
||||
'with the Glance ID, http:// or file:// URL of the '
|
||||
'initramfs of the default rescue image.')),
|
||||
cfg.StrOpt('rescue_password_hash_algorithm',
|
||||
default='sha256',
|
||||
choices=['sha256', 'sha512'],
|
||||
|
@ -447,9 +447,24 @@ def get_agent_kernel_ramdisk(node, mode='deploy', deprecated_prefix=None):
|
||||
# from driver_info but deploy_ramdisk comes from configuration,
|
||||
# since it's a sign of a potential operator's mistake.
|
||||
if not kernel or not ramdisk:
|
||||
# NOTE(kubajj): If kernel and/or ramdisk are specified by architecture,
|
||||
# prioritise them, otherwise use the default.
|
||||
kernel_dict_param_name = f'{mode}_kernel_by_arch'
|
||||
ramdisk_dict_param_name = f'{mode}_ramdisk_by_arch'
|
||||
kernel_dict = getattr(CONF.conductor, kernel_dict_param_name)
|
||||
ramdisk_dict = getattr(CONF.conductor, ramdisk_dict_param_name)
|
||||
cpu_arch = node.properties.get('cpu_arch')
|
||||
kernel_for_this_arch = kernel_dict.get(cpu_arch)
|
||||
ramdisk_for_this_arch = ramdisk_dict.get(cpu_arch)
|
||||
if kernel_for_this_arch and ramdisk_for_this_arch:
|
||||
kernel = kernel_for_this_arch
|
||||
ramdisk = ramdisk_for_this_arch
|
||||
else:
|
||||
kernel = getattr(CONF.conductor, kernel_name)
|
||||
ramdisk = getattr(CONF.conductor, ramdisk_name)
|
||||
return {
|
||||
kernel_name: getattr(CONF.conductor, kernel_name),
|
||||
ramdisk_name: getattr(CONF.conductor, ramdisk_name),
|
||||
kernel_name: kernel,
|
||||
ramdisk_name: ramdisk,
|
||||
}
|
||||
else:
|
||||
return {
|
||||
|
@ -1197,12 +1197,21 @@ class PXEInterfacesTestCase(db_base.DbTestCase):
|
||||
def test_parse_driver_info_rescue(self):
|
||||
self._test_parse_driver_info(mode='rescue')
|
||||
|
||||
def _test_parse_driver_info_from_conf(self, mode='deploy'):
|
||||
def _test_parse_driver_info_from_conf(self, mode='deploy', by_arch=False):
|
||||
ramdisk = 'glance://%s_ramdisk_uuid' % mode
|
||||
kernel = 'glance://%s_kernel_uuid' % mode
|
||||
if by_arch:
|
||||
exp_info = {'%s_ramdisk' % mode: ramdisk,
|
||||
'%s_kernel' % mode: kernel}
|
||||
config = {'%s_ramdisk_by_arch' % mode: ramdisk,
|
||||
'%s_kernel_by_arch' % mode: kernel}
|
||||
else:
|
||||
del self.node.driver_info['%s_kernel' % mode]
|
||||
del self.node.driver_info['%s_ramdisk' % mode]
|
||||
exp_info = {'%s_ramdisk' % mode: 'glance://%s_ramdisk_uuid' % mode,
|
||||
'%s_kernel' % mode: 'glance://%s_kernel_uuid' % mode}
|
||||
self.config(group='conductor', **exp_info)
|
||||
exp_info = {'%s_ramdisk' % mode: ramdisk,
|
||||
'%s_kernel' % mode: kernel}
|
||||
config = exp_info
|
||||
self.config(group='conductor', **config)
|
||||
image_info = pxe_utils.parse_driver_info(self.node, mode=mode)
|
||||
self.assertEqual(exp_info, image_info)
|
||||
|
||||
@ -1212,12 +1221,24 @@ class PXEInterfacesTestCase(db_base.DbTestCase):
|
||||
def test_parse_driver_info_from_conf_rescue(self):
|
||||
self._test_parse_driver_info_from_conf(mode='rescue')
|
||||
|
||||
def test_parse_driver_info_from_conf_deploy_by_arch(self):
|
||||
self._test_parse_driver_info_from_conf(by_arch=True)
|
||||
|
||||
def test_parse_driver_info_from_conf_rescue_by_arch(self):
|
||||
self._test_parse_driver_info_from_conf(mode='rescue', by_arch=True)
|
||||
|
||||
def test_parse_driver_info_mixed_source_deploy(self):
|
||||
self.config(deploy_kernel='file:///image',
|
||||
deploy_ramdisk='file:///image',
|
||||
group='conductor')
|
||||
self._test_parse_driver_info_missing_ramdisk()
|
||||
|
||||
def test_parse_driver_info_mixed_source_deploy_by_arch(self):
|
||||
self.config(deploy_kernel_by_arch={'x86_64': 'file:///image'},
|
||||
deploy_ramdisk_by_arch={'x86_64': 'file:///image'},
|
||||
group='conductor')
|
||||
self._test_parse_driver_info_missing_ramdisk()
|
||||
|
||||
def test_parse_driver_info_mixed_source_rescue(self):
|
||||
self.config(rescue_kernel='file:///image',
|
||||
rescue_ramdisk='file:///image',
|
||||
|
@ -127,6 +127,20 @@ class IloBootCommonMethodsTestCase(test_common.BaseIloTest):
|
||||
actual_driver_info = ilo_boot.parse_driver_info(self.node)
|
||||
self.assertEqual(expected_driver_info, actual_driver_info)
|
||||
|
||||
def test_parse_driver_info_deploy_config_by_arch(self):
|
||||
CONF.set_override('deploy_kernel_by_arch', {'x86_64': 'kernel'},
|
||||
'conductor')
|
||||
CONF.set_override('deploy_ramdisk_by_arch', {'x86_64': 'ramdisk'},
|
||||
'conductor')
|
||||
CONF.set_override('bootloader', 'bootloader', 'conductor')
|
||||
expected_driver_info = {'deploy_kernel': 'kernel',
|
||||
'deploy_ramdisk': 'ramdisk',
|
||||
'bootloader': 'bootloader',
|
||||
'kernel_append_params': None}
|
||||
|
||||
actual_driver_info = ilo_boot.parse_driver_info(self.node)
|
||||
self.assertEqual(expected_driver_info, actual_driver_info)
|
||||
|
||||
def test_parse_driver_info_rescue_config(self):
|
||||
CONF.set_override('rescue_kernel', 'kernel', 'conductor')
|
||||
CONF.set_override('rescue_ramdisk', 'ramdisk', 'conductor')
|
||||
@ -145,6 +159,14 @@ class IloBootCommonMethodsTestCase(test_common.BaseIloTest):
|
||||
self.assertRaisesRegex(exception.MissingParameterValue, 'bootloader',
|
||||
ilo_boot.parse_driver_info, self.node)
|
||||
|
||||
def test_parse_driver_info_bootloader_none_by_arch(self):
|
||||
CONF.set_override('deploy_kernel_by_arch', {'x86_64': 'kernel'},
|
||||
'conductor')
|
||||
CONF.set_override('deploy_ramdisk_by_arch', {'x86_64': 'ramdisk'},
|
||||
'conductor')
|
||||
self.assertRaisesRegex(exception.MissingParameterValue, 'bootloader',
|
||||
ilo_boot.parse_driver_info, self.node)
|
||||
|
||||
def test_parse_driver_info_exc(self):
|
||||
self.assertRaises(exception.MissingParameterValue,
|
||||
ilo_boot.parse_driver_info, self.node)
|
||||
|
@ -158,18 +158,32 @@ class RedfishVirtualMediaBootTestCase(db_base.DbTestCase):
|
||||
redfish_boot._parse_driver_info,
|
||||
task.node)
|
||||
|
||||
def _test_parse_driver_info_from_conf(self, mode='deploy'):
|
||||
def _test_parse_driver_info_from_conf(self, mode='deploy', by_arch=False):
|
||||
with task_manager.acquire(self.context, self.node.uuid,
|
||||
shared=True) as task:
|
||||
if mode == 'rescue':
|
||||
task.node.provision_state = states.RESCUING
|
||||
|
||||
if by_arch:
|
||||
ramdisk = 'glance://%s_ramdisk_uuid' % mode
|
||||
kernel = 'glance://%s_kernel_uuid' % mode
|
||||
|
||||
config = {
|
||||
'%s_ramdisk_by_arch' % mode: {'x86_64': ramdisk},
|
||||
'%s_kernel_by_arch' % mode: {'x86_64': kernel}
|
||||
}
|
||||
expected = {
|
||||
'%s_ramdisk' % mode: ramdisk,
|
||||
'%s_kernel' % mode: kernel
|
||||
}
|
||||
else:
|
||||
expected = {
|
||||
'%s_ramdisk' % mode: 'glance://%s_ramdisk_uuid' % mode,
|
||||
'%s_kernel' % mode: 'glance://%s_kernel_uuid' % mode
|
||||
}
|
||||
config = expected
|
||||
|
||||
self.config(group='conductor', **expected)
|
||||
self.config(group='conductor', **config)
|
||||
|
||||
image_info = redfish_boot._parse_driver_info(task.node)
|
||||
|
||||
@ -182,12 +196,26 @@ class RedfishVirtualMediaBootTestCase(db_base.DbTestCase):
|
||||
def test_parse_driver_info_from_conf_rescue(self):
|
||||
self._test_parse_driver_info_from_conf(mode='rescue')
|
||||
|
||||
def _test_parse_driver_info_mixed_source(self, mode='deploy'):
|
||||
def test_parse_driver_info_from_conf_deploy_by_arch(self):
|
||||
self._test_parse_driver_info_from_conf(by_arch=True)
|
||||
|
||||
def test_parse_driver_info_from_conf_rescue_by_arch(self):
|
||||
self._test_parse_driver_info_from_conf(mode='rescue', by_arch=True)
|
||||
|
||||
def _test_parse_driver_info_mixed_source(self, mode='deploy',
|
||||
by_arch=False):
|
||||
with task_manager.acquire(self.context, self.node.uuid,
|
||||
shared=True) as task:
|
||||
if mode == 'rescue':
|
||||
task.node.provision_state = states.RESCUING
|
||||
|
||||
if by_arch:
|
||||
kernel_config = {
|
||||
'%s_kernel_by_arch' % mode: {
|
||||
'x86': 'glance://%s_kernel_uuid' % mode
|
||||
}
|
||||
}
|
||||
else:
|
||||
kernel_config = {
|
||||
'%s_kernel' % mode: 'glance://%s_kernel_uuid' % mode
|
||||
}
|
||||
@ -209,6 +237,98 @@ class RedfishVirtualMediaBootTestCase(db_base.DbTestCase):
|
||||
def test_parse_driver_info_mixed_source_rescue(self):
|
||||
self._test_parse_driver_info_mixed_source(mode='rescue')
|
||||
|
||||
def test_parse_driver_info_mixed_source_deploy_by_arch(self):
|
||||
self._test_parse_driver_info_mixed_source(by_arch=True)
|
||||
|
||||
def test_parse_driver_info_mixed_source_rescue_by_arch(self):
|
||||
self._test_parse_driver_info_mixed_source(mode='rescue', by_arch=True)
|
||||
|
||||
def _test_parse_driver_info_choose_by_arch(self, mode='deploy'):
|
||||
with task_manager.acquire(self.context, self.node.uuid,
|
||||
shared=True) as task:
|
||||
if mode == 'rescue':
|
||||
task.node.provision_state = states.RESCUING
|
||||
task.node.properties['cpu_arch'] = 'aarch64'
|
||||
wrong_ramdisk = 'glance://wrong_%s_ramdisk_uuid' % mode
|
||||
wrong_kernel = 'glance://wrong_%s_kernel_uuid' % mode
|
||||
ramdisk = 'glance://%s_ramdisk_uuid' % mode
|
||||
kernel = 'glance://%s_kernel_uuid' % mode
|
||||
|
||||
config = {
|
||||
'%s_ramdisk_by_arch' % mode: {
|
||||
'x86_64': wrong_ramdisk, 'aarch64': ramdisk},
|
||||
'%s_kernel_by_arch' % mode: {
|
||||
'x86_64': wrong_kernel, 'aarch64': kernel}
|
||||
}
|
||||
expected = {
|
||||
'%s_ramdisk' % mode: ramdisk,
|
||||
'%s_kernel' % mode: kernel
|
||||
}
|
||||
|
||||
self.config(group='conductor', **config)
|
||||
|
||||
image_info = redfish_boot._parse_driver_info(task.node)
|
||||
|
||||
for key, value in expected.items():
|
||||
self.assertEqual(value, image_info[key])
|
||||
|
||||
def test_parse_driver_info_choose_by_arch_deploy(self):
|
||||
self._test_parse_driver_info_choose_by_arch()
|
||||
|
||||
def test_parse_driver_info_choose_by_arch_rescue(self):
|
||||
self._test_parse_driver_info_choose_by_arch(mode='rescue')
|
||||
|
||||
def _test_parse_driver_info_choose_by_hierarchy(self, mode='deploy',
|
||||
ramdisk_missing=False):
|
||||
with task_manager.acquire(self.context, self.node.uuid,
|
||||
shared=True) as task:
|
||||
if mode == 'rescue':
|
||||
task.node.provision_state = states.RESCUING
|
||||
|
||||
ramdisk = 'glance://def_%s_ramdisk_uuid' % mode
|
||||
kernel = 'glance://def_%s_kernel_uuid' % mode
|
||||
ramdisk_by_arch = 'glance://%s_ramdisk_by_arch_uuid' % mode
|
||||
kernel_by_arch = 'glance://%s_kernel_by_arch_uuid' % mode
|
||||
|
||||
config = {
|
||||
'%s_kernel_by_arch' % mode: {
|
||||
'x86_64': kernel_by_arch},
|
||||
'%s_ramdisk' % mode: ramdisk,
|
||||
'%s_kernel' % mode: kernel
|
||||
}
|
||||
if not ramdisk_missing:
|
||||
config['%s_ramdisk_by_arch' % mode] = {
|
||||
'x86_64': ramdisk_by_arch}
|
||||
expected = {
|
||||
'%s_ramdisk' % mode: ramdisk_by_arch,
|
||||
'%s_kernel' % mode: kernel_by_arch
|
||||
}
|
||||
else:
|
||||
expected = {
|
||||
'%s_ramdisk' % mode: ramdisk,
|
||||
'%s_kernel' % mode: kernel
|
||||
}
|
||||
|
||||
self.config(group='conductor', **config)
|
||||
|
||||
image_info = redfish_boot._parse_driver_info(task.node)
|
||||
|
||||
for key, value in expected.items():
|
||||
self.assertEqual(value, image_info[key])
|
||||
|
||||
def test_parse_driver_info_choose_by_hierarchy_deploy(self):
|
||||
self._test_parse_driver_info_choose_by_hierarchy()
|
||||
|
||||
def test_parse_driver_info_choose_by_hierarchy_rescue(self):
|
||||
self._test_parse_driver_info_choose_by_hierarchy(mode='rescue')
|
||||
|
||||
def test_parse_driver_info_choose_by_hierarchy_missing_param_deploy(self):
|
||||
self._test_parse_driver_info_choose_by_hierarchy(ramdisk_missing=True)
|
||||
|
||||
def test_parse_driver_info_choose_by_hierarchy_missing_param_rescue(self):
|
||||
self._test_parse_driver_info_choose_by_hierarchy(
|
||||
mode='rescue', ramdisk_missing=True)
|
||||
|
||||
def test_parse_deploy_info(self):
|
||||
with task_manager.acquire(self.context, self.node.uuid,
|
||||
shared=True) as task:
|
||||
|
@ -0,0 +1,13 @@
|
||||
---
|
||||
features:
|
||||
- |
|
||||
Introduce new config parameters in the conductor group.
|
||||
The `deploy_kernel_by_arch`, `deploy_ramdisk_by_arch`,
|
||||
`rescue_kernel_by_arch`, and `rescue_ramdisk_by_arch` are dictionaries
|
||||
allowing operators to specify parameters of kernel and ramdisk by the
|
||||
architecture of the node.
|
||||
deprecations:
|
||||
- |
|
||||
The `deploy_kernel`, `deploy_ramdisk`, `rescue_kernel`, and
|
||||
`rescue_ramdisk` parameters have been marked as deprecated as the new
|
||||
parameters allow more configuration options.
|
Loading…
Reference in New Issue
Block a user