Add new boot interface in Ironic
This commit proposes to add new boot interface in Ironic and refactor the current upstream deploy drivers to follow this logic. Change-Id: Ie7321b925397e3185dde654b21660a63eed0fd9f
This commit is contained in:
parent
2e27b16688
commit
24153185f1
273
specs/liberty/new-boot-interface.rst
Normal file
273
specs/liberty/new-boot-interface.rst
Normal file
@ -0,0 +1,273 @@
|
||||
..
|
||||
This work is licensed under a Creative Commons Attribution 3.0 Unported
|
||||
License.
|
||||
|
||||
http://creativecommons.org/licenses/by/3.0/legalcode
|
||||
|
||||
========================
|
||||
Boot Interface in Ironic
|
||||
========================
|
||||
|
||||
https://blueprints.launchpad.net/ironic/+spec/new-boot-interface
|
||||
|
||||
This spec talks about refactoring the boot logic out of the current Ironic
|
||||
"deploy" drivers into a new boot interface.
|
||||
|
||||
Problem description
|
||||
===================
|
||||
|
||||
Current we have a DeployInterface in Ironic. All the current implementations
|
||||
of this interface are responsible for two things:
|
||||
|
||||
* Booting the bare metal node - both deploy ramdisk and the deployed instance.
|
||||
* Actual deployment of an image on a bare metal node.
|
||||
|
||||
These are two separate functions and therefore should be abstracted
|
||||
separately. This makes it easy to mix and match various boot mechanisms (like
|
||||
PXE, iPXE, virtual media) with various deploy mechanisms (iscsi deploy, agent
|
||||
deploy and various other deploy mechanisms which may be possible like
|
||||
deploying with torrent, multicast, etc in which discussions have been
|
||||
initiated) without duplicating code.
|
||||
|
||||
Proposed change
|
||||
===============
|
||||
|
||||
* A new ``BootInterface`` needs to be added. The interface will recommend the
|
||||
following methods for the implementor::
|
||||
|
||||
@six.add_metaclass(abc.ABCMeta)
|
||||
class BootInterface(object):
|
||||
"""Interface for inspection-related actions."""
|
||||
|
||||
@abc.abstractmethod
|
||||
def get_properties(self):
|
||||
"""Return the properties of the interface.
|
||||
|
||||
:returns: dictionary of <property name>:<property description>
|
||||
"""
|
||||
|
||||
@abc.abstractmethod
|
||||
def validate(self, task):
|
||||
"""Validate the driver-specific info for booting.
|
||||
|
||||
This method validates the driver-specific info for booting a ramdisk
|
||||
and an instance on the node. If invalid, raises an exception;
|
||||
otherwise returns None.
|
||||
|
||||
:param task: a task from TaskManager.
|
||||
:raises: InvalidParameterValue
|
||||
:raises: MissingParameterValue
|
||||
"""
|
||||
|
||||
@abc.abstractmethod
|
||||
def prepare_ramdisk(self, task, ramdisk_params):
|
||||
"""Prepares the boot of Ironic ramdisk.
|
||||
|
||||
This method prepares the boot of the deploy ramdisk after reading
|
||||
relevant information from the node's database.
|
||||
|
||||
:param task: a task from TaskManager.
|
||||
:param ramdisk_params: the options to be passed to the ironic ramdisk.
|
||||
Different interfaces might want to boot the ramdisk in different
|
||||
ways by passing parameters to them. For example,
|
||||
* When DIB ramdisk is booted to deploy a node, it takes the
|
||||
parameters iscsi_target_iqn, deployment_id, ironic_api_url, etc.
|
||||
* When Agent ramdisk is booted to deploy a node, it takes the
|
||||
parameters ipa-driver-name, ipa-api-url, root_device, etc.
|
||||
Other interfaces can make use of ramdisk_params to pass such
|
||||
information. Different implementations of boot interface will
|
||||
have different ways of passing parameters to the ramdisk.
|
||||
"""
|
||||
|
||||
@abc.abstractmethod
|
||||
def clean_up_ramdisk(self, task):
|
||||
"""Tears down the boot of Ironic ramdisk.
|
||||
|
||||
This method tears down the boot of the deploy ramdisk after reading
|
||||
relevant information from the node's database.
|
||||
|
||||
:param task: a task from TaskManager.
|
||||
"""
|
||||
|
||||
@abc.abstractmethod
|
||||
def prepare_instance(self, task):
|
||||
"""Prepares the boot of instance.
|
||||
|
||||
This method prepares the boot of the instance after reading
|
||||
relevant information from the node's database.
|
||||
|
||||
:param task: a task from TaskManager.
|
||||
"""
|
||||
|
||||
@abc.abstractmethod
|
||||
def clean_up_instance(self, task):
|
||||
"""Tears down the boot of instance.
|
||||
|
||||
This method tears down the boot of the instance after reading
|
||||
relevant information from the node's database.
|
||||
|
||||
:param task: a task from TaskManager.
|
||||
"""
|
||||
|
||||
* The following new implementations of ``BootInterface`` will be created.
|
||||
|
||||
+ ``pxe.PXEBoot`` - Booting a bare metal node using PXE
|
||||
+ ``ipxe.IPXEBoot`` - Booting a bare metal node using iPXE
|
||||
+ ``ilo.boot.IloVirtualMediaBoot`` - Booting a bare metal node using iLO
|
||||
Virtual Media.
|
||||
|
||||
.. note::
|
||||
Even though IPXEBoot and PXEBoot are in same deploy driver currently, the
|
||||
steps for preparing a bare metal to boot from PXE and iPXE are different
|
||||
(even though they share some common code). We will refactor both of them
|
||||
as separate boot interfaces. The Kilo behaviour of using only either of
|
||||
PXE or iPXE at same time will be retained - drivers will instantiate
|
||||
pxe.PXEBoot or ipxe.IPXEBoot depending on CONF.pxe.ipxe_enabled.
|
||||
|
||||
* The code for the above implementations of ``BootInterface`` will be taken
|
||||
from ``pxe.PXEDeploy``, ``agent.AgentDeploy``,
|
||||
``ilo.IloVirtualMediaIscsiDeploy`` and ``ilo.IloVirtualMediaAgentDeploy``.
|
||||
These implementations of ``DeployInterface`` will be freed of any logic
|
||||
dealing with booting of bare metal node.
|
||||
|
||||
* ``pxe.PXEDeploy`` will be refactored into ``pxe.PXEBoot`` and
|
||||
``iscsi_deploy.ISCSIDeploy``.
|
||||
|
||||
* Each driver will mention what is the ``BootInterface`` implementation that it
|
||||
wishes to instantiate. For example, the ``pxe_ipmitool`` driver will look
|
||||
like the following::
|
||||
|
||||
class PXEAndIPMIToolDriver(base.BaseDriver):
|
||||
"""PXE + IPMITool driver"""
|
||||
|
||||
def __init__(self):
|
||||
self.power = ipmitool.IPMIPower()
|
||||
self.console = ipmitool.IPMIShellinaboxConsole()
|
||||
self.boot = pxe.PXEBoot()
|
||||
self.deploy = iscsi_deploy.ISCSIDeploy()
|
||||
self.management = ipmitool.IPMIManagement()
|
||||
self.vendor = pxe.VendorPassthru()
|
||||
self.inspect = discoverd.DiscoverdInspect.create_if_enabled(
|
||||
'PXEAndIPMIToolDriver')
|
||||
|
||||
|
||||
.. note::
|
||||
|
||||
It might make sense to rename the drivers to include the boot interface as
|
||||
well as deploy interface after this is implemented. As such, this requires
|
||||
a better thought out process to rename the drivers, address issues of
|
||||
backward compatibility, etc. Hence it is out of scope of this spec. That
|
||||
can be addressed later after this is implemented.
|
||||
|
||||
Alternatives
|
||||
------------
|
||||
We can continue to keep the boot and deploy logic together but this will
|
||||
lead to code duplications and unnecessary refactorings when additional deploy
|
||||
mechanisms and boot mechanisms are added in the future.
|
||||
|
||||
Data model impact
|
||||
-----------------
|
||||
None.
|
||||
|
||||
State Machine Impact
|
||||
--------------------
|
||||
None.
|
||||
|
||||
REST API impact
|
||||
---------------
|
||||
None.
|
||||
|
||||
RPC API impact
|
||||
--------------
|
||||
None.
|
||||
|
||||
Client (CLI) impact
|
||||
-------------------
|
||||
None.
|
||||
|
||||
Driver API impact
|
||||
-----------------
|
||||
This adds the a new ``BootInterface`` (as described above) which driver
|
||||
writers may use with the deploy drivers. ``BootInterface`` is not a
|
||||
mandatory interface.
|
||||
|
||||
Nova driver impact
|
||||
------------------
|
||||
None.
|
||||
|
||||
Security impact
|
||||
---------------
|
||||
None.
|
||||
|
||||
Other end user impact
|
||||
---------------------
|
||||
None.
|
||||
|
||||
Scalability impact
|
||||
------------------
|
||||
None.
|
||||
|
||||
Performance Impact
|
||||
------------------
|
||||
None.
|
||||
|
||||
Other deployer impact
|
||||
---------------------
|
||||
None.
|
||||
|
||||
Developer impact
|
||||
----------------
|
||||
New driver developers adding new deploy mechanisms in Ironic will be
|
||||
encouraged to separate boot and deploy logic so that it can reused easily.
|
||||
|
||||
Implementation
|
||||
==============
|
||||
|
||||
Assignee(s)
|
||||
-----------
|
||||
rameshg87
|
||||
|
||||
Work Items
|
||||
----------
|
||||
* Add new boot interface
|
||||
* Create ``pxe.PXEBoot``, ``ipxe.IPXEBoot`` and refactor ``pxe.PXEDeploy``
|
||||
into ``iscsi_deploy.ISCSIDeploy`` to make use of these boot interfaces.
|
||||
* Refactor ``agent.AgentDeploy`` to use new ``pxe.PXEBoot`` and
|
||||
``ipxe.IPXEBoot`` (Yes, we are adding iPXE support for agent deploy).
|
||||
* Create ``ilo.boot.IloVirtualMediaBoot``, and refactor
|
||||
``IloVirtualMediaIscsiDriver``, ``IloVirtualMediaAgentDriver`` to make
|
||||
use of the new boot interface.
|
||||
|
||||
Dependencies
|
||||
============
|
||||
None.
|
||||
|
||||
Testing
|
||||
=======
|
||||
Unit tests will be updated for the new interfaces. Since this change doesn't
|
||||
add any new functionality, the current upstream CI testing should be enough.
|
||||
|
||||
Upgrades and Backwards Compatibility
|
||||
====================================
|
||||
This doesn't break out-of-tree deploy drivers. Still it will be possible
|
||||
to implement deploy drivers for provisioning bare metal nodes without a boot
|
||||
interface- i.e without separate boot and deploy interfaces. This is because
|
||||
the conductor will still be using all the published interfaces of
|
||||
``DeployInterface`` for deploying a bare metal node.
|
||||
|
||||
This change proposes the addition of new optional boot interface which can be
|
||||
used as a helper for ``DeployInterface`` and refactors all upstream deploy
|
||||
drivers to follow this logic.
|
||||
|
||||
Documentation Impact
|
||||
====================
|
||||
Changes to the existing interface will be documented. Also, new developer
|
||||
documentation will be updated to encourage splitting deploy logic into separate
|
||||
boot and deploy interfaces.
|
||||
|
||||
References
|
||||
==========
|
||||
Not according to this spec, but a POC how it will look like:
|
||||
* https://review.openstack.org/#/c/166512/
|
||||
* https://review.openstack.org/#/c/166513/
|
||||
* https://review.openstack.org/#/c/166521/
|
Loading…
Reference in New Issue
Block a user