Workaround to fix Heat stack deletion bug in Shade 89/52189/2
authorRodolfo Alonso Hernandez <rodolfo.alonso.hernandez@intel.com>
Thu, 15 Feb 2018 11:42:11 +0000 (11:42 +0000)
committerRodolfo Alonso Hernandez <rodolfo.alonso.hernandez@intel.com>
Thu, 15 Feb 2018 11:55:08 +0000 (11:55 +0000)
There is a bug in Shade, in the function "event_utils.poll_for_events".
While Shade is waiting for the Heat stack to be deleted, retrieves
periodically the status of this Heat stack. When the stack is deleted,
the function "get_stack" [1] returns None; then L90 tries to access to
a key of this None object.

[1]https://github.com/openstack-infra/shade/blob/e5bcb705c5b32334cdc1dd9807126298c87b0622/shade/_heat/event_utils.py#L89-L90
Shade function

JIRA: YARDSTICK-1015

Change-Id: I56ea853be41bfd7f63e094d7a3696d97ba078ba4
Signed-off-by: Rodolfo Alonso Hernandez <rodolfo.alonso.hernandez@intel.com>
yardstick/orchestrator/heat.py
yardstick/tests/unit/orchestrator/test_heat.py

index 754482e..558b5d2 100644 (file)
@@ -74,7 +74,14 @@ class HeatStack(object):
         if self.uuid is None:
             return
 
-        ret = self._cloud.delete_stack(self.uuid, wait=wait)
+        try:
+            ret = self._cloud.delete_stack(self.uuid, wait=wait)
+        except TypeError:
+            # NOTE(ralonsoh): this exception catch solves a bug in Shade, which
+            # tries to retrieve and read the stack status when it's already
+            # deleted.
+            ret = True
+
         _DEPLOYED_STACKS.pop(self.uuid)
         self._stack = None
         return ret
index f53c9b7..e0a3538 100644 (file)
@@ -89,6 +89,18 @@ class HeatStackTestCase(unittest.TestCase):
         self.assertFalse(heat._DEPLOYED_STACKS)
         self.mock_stack_delete.assert_called_once_with(id, wait=True)
 
+    def test_delete_bug_in_shade(self):
+        id = uuidutils.generate_uuid()
+        self.heatstack._stack = FakeStack(
+            outputs=mock.Mock(), status=mock.Mock(), id=id)
+        heat._DEPLOYED_STACKS[id] = self.heatstack._stack
+        self.mock_stack_delete.side_effect = TypeError()
+
+        ret = self.heatstack.delete(wait=True)
+        self.assertTrue(ret)
+        self.assertFalse(heat._DEPLOYED_STACKS)
+        self.mock_stack_delete.assert_called_once_with(id, wait=True)
+
 
 class HeatTemplateTestCase(unittest.TestCase):