From a15c10ef1ace5830bacdeeb42aeaea4b6bcfa123 Mon Sep 17 00:00:00 2001 From: Mike Fedosin Date: Wed, 20 Dec 2017 22:02:38 +0100 Subject: [PATCH] Remove "overcloud-swift-rings" container during overcloud deletion MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Trying to re-run `openstack overcloud deploy` now fails with "A container with the name overcloud-swift-rings already exists." It happens because Ьistral doesn't remove the container during the deletion process. This patch adds the removal of the container to the corresponding action. Change-Id: I3f62fc61758cb817c45df8e67ed3639934edd038 Closes-bug: #1738437 --- tripleo_common/actions/plan.py | 2 ++ tripleo_common/tests/actions/test_plan.py | 35 ++++++++++++++++++++++- tripleo_common/utils/swift.py | 9 ++++-- 3 files changed, 43 insertions(+), 3 deletions(-) diff --git a/tripleo_common/actions/plan.py b/tripleo_common/actions/plan.py index d4706d991..c92e158fb 100644 --- a/tripleo_common/actions/plan.py +++ b/tripleo_common/actions/plan.py @@ -119,6 +119,8 @@ class DeletePlanAction(base.TripleOAction): try: swift = self.get_object_client(context) swiftutils.delete_container(swift, self.container) + swiftutils.delete_container(swift, + "%s-swift-rings" % self.container) except swiftexceptions.ClientException as ce: LOG.exception("Swift error deleting plan.") error_text = ce.msg diff --git a/tripleo_common/tests/actions/test_plan.py b/tripleo_common/tests/actions/test_plan.py index 5205bc543..2a04e44f9 100644 --- a/tripleo_common/tests/actions/test_plan.py +++ b/tripleo_common/tests/actions/test_plan.py @@ -201,6 +201,7 @@ class DeletePlanActionTest(base.TestCase): swift = mock.MagicMock() swift.get_account.return_value = ({}, [ {'name': self.container_name}, + {'name': "%s-swift-rings" % self.container_name}, {'name': 'test'}, ]) swift.get_container.return_value = ( @@ -232,7 +233,39 @@ class DeletePlanActionTest(base.TestCase): swift.delete_object.assert_has_calls( mock_calls, any_order=True) - swift.delete_container.assert_called_with(self.container_name) + mock_calls = [ + mock.call(self.container_name), + mock.call("%s-swift-rings" % self.container_name) + ] + self.assertEqual(2, swift.delete_container.call_count) + swift.delete_container.assert_has_calls(mock_calls) + + @mock.patch('tripleo_common.actions.base.TripleOAction.get_object_client') + @mock.patch( + 'tripleo_common.actions.base.TripleOAction.get_orchestration_client') + def test_run_no_containers( + self, get_orchestration_client, get_obj_client_mock): + + # setup swift + swift = mock.MagicMock() + # There are no swift containers because they were either accidentally + # removed or not created. + swift.get_account.return_value = ({}, []) + + get_obj_client_mock.return_value = swift + + # setup heat + heat = mock.MagicMock() + heat.stacks.get = mock.Mock( + side_effect=heatexceptions.HTTPNotFound) + get_orchestration_client.return_value = heat + + action = plan.DeletePlanAction(self.container_name) + action.run(self.ctx) + + # The operation was successfully finished and we didn't try to remove + # nonexistent containers. + self.assertEqual(0, swift.delete_container.call_count) class ListRolesActionTest(base.TestCase): diff --git a/tripleo_common/utils/swift.py b/tripleo_common/utils/swift.py index 92fe9160e..1d8c622f7 100644 --- a/tripleo_common/utils/swift.py +++ b/tripleo_common/utils/swift.py @@ -50,8 +50,13 @@ def empty_container(swiftclient, name): def delete_container(swiftclient, name): - empty_container(swiftclient, name) - swiftclient.delete_container(name) + try: + empty_container(swiftclient, name) + swiftclient.delete_container(name) + except ValueError as e: + # ValueError is raised when we can't find the container, which means + # that it's already deleted. + LOG.info(e.message) def download_container(swiftclient, container, dest):