Allow to change interfaces configuration for nodes that errored on deployment

This commit fixes the issue that it is not possible to recover after
deploying/redeploying a node with broken network interfaces config.
We allow interfaces configuration for a set of node error states
including discover and deploy actions.

Minor: Fix pep8 line length complaint.

Change-Id: I8dbaf96c1f89f77e7963d164d2ca4648bcd77fca
Closes-bug: #1592998
This commit is contained in:
Vladimir Kuklin 2016-06-16 01:30:23 +03:00
parent 1428c80b46
commit 0c836b3555
2 changed files with 28 additions and 16 deletions

View File

@ -551,6 +551,9 @@ class Node(NailgunObject):
consts.NODE_STATUSES.discover,
consts.NODE_STATUSES.error,
)
unlocked_node_error_types = (
consts.NODE_ERRORS.discover,
)
else:
unlocked_cluster_statuses = (
consts.NODE_STATUSES.discover,
@ -558,10 +561,14 @@ class Node(NailgunObject):
consts.NODE_STATUSES.stopped,
consts.NODE_STATUSES.ready
)
unlocked_node_error_types = (
consts.NODE_ERRORS.discover,
consts.NODE_ERRORS.deploy
)
return instance.status not in unlocked_cluster_statuses or (
instance.status == consts.NODE_STATUSES.error and
instance.error_type != consts.NODE_ERRORS.discover
instance.error_type not in unlocked_node_error_types
)
@classmethod
@ -869,7 +876,7 @@ class Node(NailgunObject):
instance.human_readable_name)
meta['disks'] = instance.meta['disks']
if not cls.is_interfaces_configuration_locked(instance, is_agent=True) \
if not cls.is_interfaces_configuration_locked(instance, is_agent=True)\
and data.get('ip'):
if instance.cluster_id:
update_status = cls.check_ip_belongs_to_own_admin_network(

View File

@ -14,8 +14,6 @@
# License for the specific language governing permissions and limitations
# under the License.
import six
from oslo_serialization import jsonutils
from nailgun import consts
@ -125,15 +123,20 @@ class TestNodeCollectionNICsHandler(BaseIntegrationTest):
self.assertEquals(1, len(changes))
def test_interface_changes_locking(self):
lock_vs_status = {
consts.NODE_STATUSES.discover: False,
consts.NODE_STATUSES.error: True,
consts.NODE_STATUSES.provisioning: True,
consts.NODE_STATUSES.provisioned: True,
consts.NODE_STATUSES.deploying: True,
consts.NODE_STATUSES.ready: False,
consts.NODE_STATUSES.stopped: False,
consts.NODE_STATUSES.removing: True}
lock_vs_status = (
(consts.NODE_STATUSES.discover, False),
(consts.NODE_STATUSES.error, False, consts.NODE_ERRORS.deploy),
(consts.NODE_STATUSES.error, True, consts.NODE_ERRORS.provision),
(consts.NODE_STATUSES.error, False, consts.NODE_ERRORS.discover),
(consts.NODE_STATUSES.error, True,
consts.NODE_ERRORS.stop_deployment),
(consts.NODE_STATUSES.error, True, consts.NODE_ERRORS.deletion),
(consts.NODE_STATUSES.provisioning, True),
(consts.NODE_STATUSES.provisioned, True),
(consts.NODE_STATUSES.deploying, True),
(consts.NODE_STATUSES.ready, False),
(consts.NODE_STATUSES.stopped, False),
(consts.NODE_STATUSES.removing, True))
meta = self.env.default_metadata()
meta['interfaces'] = [{'name': 'eth0', 'pxe': True},
{'name': 'eth1'}]
@ -141,9 +144,11 @@ class TestNodeCollectionNICsHandler(BaseIntegrationTest):
nodes_kwargs=[{'roles': ['controller'], 'meta': meta}]
)
node = self.env.nodes[0]
node.error_type = consts.NODE_ERRORS.deploy
for status, lock in six.iteritems(lock_vs_status):
node.status = status
for case in lock_vs_status:
node.status = case[0]
lock = case[1]
if node.status == consts.NODE_STATUSES.error:
node.error_type = case[2]
self.db.flush()
# Getting nics
resp = self.env.node_nics_get(node.id)