Support for protected and protected_reason fields
Story: #2003869 Task: #27624 Depends-On: https://review.openstack.org/611662 Change-Id: Ib575ace38d1bedce54d0d21517d745ed3204d6f2
This commit is contained in:
parent
9325743c0d
commit
1c941eefe5
@ -43,7 +43,7 @@ from ironicclient import exc
|
|||||||
# http://specs.openstack.org/openstack/ironic-specs/specs/kilo/api-microversions.html # noqa
|
# http://specs.openstack.org/openstack/ironic-specs/specs/kilo/api-microversions.html # noqa
|
||||||
# for full details.
|
# for full details.
|
||||||
DEFAULT_VER = '1.9'
|
DEFAULT_VER = '1.9'
|
||||||
LAST_KNOWN_API_VERSION = 47
|
LAST_KNOWN_API_VERSION = 48
|
||||||
LATEST_VERSION = '1.{}'.format(LAST_KNOWN_API_VERSION)
|
LATEST_VERSION = '1.{}'.format(LAST_KNOWN_API_VERSION)
|
||||||
|
|
||||||
LOG = logging.getLogger(__name__)
|
LOG = logging.getLogger(__name__)
|
||||||
|
@ -1116,6 +1116,16 @@ class SetBaremetalNode(command.Command):
|
|||||||
action='store_true',
|
action='store_true',
|
||||||
help=_('Enable automated cleaning for the node'),
|
help=_('Enable automated cleaning for the node'),
|
||||||
)
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--protected',
|
||||||
|
action='store_true',
|
||||||
|
help=_('Mark the node as protected'),
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--protected-reason',
|
||||||
|
metavar='<protected_reason>',
|
||||||
|
help=_('Set the reason of marking the node as protected'),
|
||||||
|
)
|
||||||
parser.add_argument(
|
parser.add_argument(
|
||||||
'--target-raid-config',
|
'--target-raid-config',
|
||||||
metavar='<target_raid_config>',
|
metavar='<target_raid_config>',
|
||||||
@ -1174,7 +1184,7 @@ class SetBaremetalNode(command.Command):
|
|||||||
properties = []
|
properties = []
|
||||||
for field in ['automated_clean', 'instance_uuid', 'name',
|
for field in ['automated_clean', 'instance_uuid', 'name',
|
||||||
'chassis_uuid', 'driver', 'resource_class',
|
'chassis_uuid', 'driver', 'resource_class',
|
||||||
'conductor_group']:
|
'conductor_group', 'protected', 'protected_reason']:
|
||||||
value = getattr(parsed_args, field)
|
value = getattr(parsed_args, field)
|
||||||
if value:
|
if value:
|
||||||
properties.extend(utils.args_array_to_patch(
|
properties.extend(utils.args_array_to_patch(
|
||||||
@ -1436,6 +1446,17 @@ class UnsetBaremetalNode(command.Command):
|
|||||||
help=_('Unset automated clean option on this baremetal node '
|
help=_('Unset automated clean option on this baremetal node '
|
||||||
'(the value from configuration will be used)'),
|
'(the value from configuration will be used)'),
|
||||||
)
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
"--protected",
|
||||||
|
action="store_true",
|
||||||
|
help=_('Unset the protected flag on the node'),
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
"--protected-reason",
|
||||||
|
action="store_true",
|
||||||
|
help=_('Unset the protected reason (gets unset automatically when '
|
||||||
|
'protected is unset)'),
|
||||||
|
)
|
||||||
|
|
||||||
return parser
|
return parser
|
||||||
|
|
||||||
@ -1457,7 +1478,8 @@ class UnsetBaremetalNode(command.Command):
|
|||||||
'deploy_interface', 'inspect_interface',
|
'deploy_interface', 'inspect_interface',
|
||||||
'management_interface', 'network_interface',
|
'management_interface', 'network_interface',
|
||||||
'power_interface', 'raid_interface', 'rescue_interface',
|
'power_interface', 'raid_interface', 'rescue_interface',
|
||||||
'storage_interface', 'vendor_interface']:
|
'storage_interface', 'vendor_interface',
|
||||||
|
'protected', 'protected_reason']:
|
||||||
if getattr(parsed_args, field):
|
if getattr(parsed_args, field):
|
||||||
properties.extend(utils.args_array_to_patch('remove', [field]))
|
properties.extend(utils.args_array_to_patch('remove', [field]))
|
||||||
|
|
||||||
|
@ -636,6 +636,8 @@ class TestBaremetalList(TestBaremetal):
|
|||||||
'Power Interface',
|
'Power Interface',
|
||||||
'Power State',
|
'Power State',
|
||||||
'Properties',
|
'Properties',
|
||||||
|
'Protected',
|
||||||
|
'Protected Reason',
|
||||||
'Provision Updated At',
|
'Provision Updated At',
|
||||||
'Provisioning State',
|
'Provisioning State',
|
||||||
'RAID Interface',
|
'RAID Interface',
|
||||||
@ -2303,6 +2305,49 @@ class TestBaremetalSet(TestBaremetal):
|
|||||||
reset_interfaces=None,
|
reset_interfaces=None,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def test_baremetal_set_protected(self):
|
||||||
|
arglist = [
|
||||||
|
'node_uuid',
|
||||||
|
'--protected'
|
||||||
|
]
|
||||||
|
verifylist = [
|
||||||
|
('node', 'node_uuid'),
|
||||||
|
('protected', True)
|
||||||
|
]
|
||||||
|
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
|
||||||
|
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
|
||||||
|
self.baremetal_mock.node.update.assert_called_once_with(
|
||||||
|
'node_uuid',
|
||||||
|
[{'path': '/protected', 'value': 'True', 'op': 'add'}],
|
||||||
|
reset_interfaces=None,
|
||||||
|
)
|
||||||
|
|
||||||
|
def test_baremetal_set_protected_with_reason(self):
|
||||||
|
arglist = [
|
||||||
|
'node_uuid',
|
||||||
|
'--protected',
|
||||||
|
'--protected-reason', 'reason!'
|
||||||
|
]
|
||||||
|
verifylist = [
|
||||||
|
('node', 'node_uuid'),
|
||||||
|
('protected', True),
|
||||||
|
('protected_reason', 'reason!')
|
||||||
|
]
|
||||||
|
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
|
||||||
|
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
|
||||||
|
self.baremetal_mock.node.update.assert_called_once_with(
|
||||||
|
'node_uuid',
|
||||||
|
[{'path': '/protected', 'value': 'True', 'op': 'add'},
|
||||||
|
{'path': '/protected_reason', 'value': 'reason!', 'op': 'add'}],
|
||||||
|
reset_interfaces=None,
|
||||||
|
)
|
||||||
|
|
||||||
def test_baremetal_set_extra(self):
|
def test_baremetal_set_extra(self):
|
||||||
arglist = [
|
arglist = [
|
||||||
'node_uuid',
|
'node_uuid',
|
||||||
@ -2774,6 +2819,44 @@ class TestBaremetalUnset(TestBaremetal):
|
|||||||
[{'path': '/automated_clean', 'op': 'remove'}]
|
[{'path': '/automated_clean', 'op': 'remove'}]
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def test_baremetal_unset_protected(self):
|
||||||
|
arglist = [
|
||||||
|
'node_uuid',
|
||||||
|
'--protected',
|
||||||
|
]
|
||||||
|
verifylist = [
|
||||||
|
('node', 'node_uuid'),
|
||||||
|
('protected', True)
|
||||||
|
]
|
||||||
|
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
|
||||||
|
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
|
||||||
|
self.baremetal_mock.node.update.assert_called_once_with(
|
||||||
|
'node_uuid',
|
||||||
|
[{'path': '/protected', 'op': 'remove'}]
|
||||||
|
)
|
||||||
|
|
||||||
|
def test_baremetal_unset_protected_reason(self):
|
||||||
|
arglist = [
|
||||||
|
'node_uuid',
|
||||||
|
'--protected-reason',
|
||||||
|
]
|
||||||
|
verifylist = [
|
||||||
|
('node', 'node_uuid'),
|
||||||
|
('protected_reason', True)
|
||||||
|
]
|
||||||
|
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, verifylist)
|
||||||
|
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
|
||||||
|
self.baremetal_mock.node.update.assert_called_once_with(
|
||||||
|
'node_uuid',
|
||||||
|
[{'path': '/protected_reason', 'op': 'remove'}]
|
||||||
|
)
|
||||||
|
|
||||||
def test_baremetal_unset_extra(self):
|
def test_baremetal_unset_extra(self):
|
||||||
arglist = [
|
arglist = [
|
||||||
'node_uuid',
|
'node_uuid',
|
||||||
|
@ -65,6 +65,8 @@ class NodeShellTest(utils.BaseTestCase):
|
|||||||
'vendor_interface',
|
'vendor_interface',
|
||||||
'power_state',
|
'power_state',
|
||||||
'properties',
|
'properties',
|
||||||
|
'protected',
|
||||||
|
'protected_reason',
|
||||||
'provision_state',
|
'provision_state',
|
||||||
'provision_updated_at',
|
'provision_updated_at',
|
||||||
'reservation',
|
'reservation',
|
||||||
|
@ -89,6 +89,8 @@ class Resource(object):
|
|||||||
'node_uuid': 'Node UUID',
|
'node_uuid': 'Node UUID',
|
||||||
'power_state': 'Power State',
|
'power_state': 'Power State',
|
||||||
'properties': 'Properties',
|
'properties': 'Properties',
|
||||||
|
'protected': 'Protected',
|
||||||
|
'protected_reason': 'Protected Reason',
|
||||||
'provision_state': 'Provisioning State',
|
'provision_state': 'Provisioning State',
|
||||||
'provision_updated_at': 'Provision Updated At',
|
'provision_updated_at': 'Provision Updated At',
|
||||||
'raid_config': 'Current RAID configuration',
|
'raid_config': 'Current RAID configuration',
|
||||||
@ -234,6 +236,8 @@ NODE_DETAILED_RESOURCE = Resource(
|
|||||||
'power_interface',
|
'power_interface',
|
||||||
'power_state',
|
'power_state',
|
||||||
'properties',
|
'properties',
|
||||||
|
'protected',
|
||||||
|
'protected_reason',
|
||||||
'provision_updated_at',
|
'provision_updated_at',
|
||||||
'provision_state',
|
'provision_state',
|
||||||
'raid_interface',
|
'raid_interface',
|
||||||
|
7
releasenotes/notes/protected-72d7419245a4f6c3.yaml
Normal file
7
releasenotes/notes/protected-72d7419245a4f6c3.yaml
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
---
|
||||||
|
features:
|
||||||
|
- |
|
||||||
|
Adds the ability to set and unset the ``protected`` and
|
||||||
|
``protected_reason`` fields introduced in API 1.48. Setting ``protected``
|
||||||
|
allows protecting a deployed node from undeploying, rebuilding and
|
||||||
|
deleting.
|
Loading…
Reference in New Issue
Block a user