Add check for non-existing table internal name for delete table
This change added check for non-existing internal name for tables which caused exception when trying to delete table in CREATE_FAILED or DELETE_FALED status if table internal name does not exist. Change-Id: I3175a364a4e678f35b860db26f9dec999997f8a0 Closes-bug: #1422908
This commit is contained in:
parent
84644abbb3
commit
0efeb6242d
|
@ -156,7 +156,21 @@ class SimpleStorageManager(manager.StorageManager):
|
|||
|
||||
self._table_info_repo.update(context, table_info, ["status"])
|
||||
|
||||
self._do_delete_table(context, table_info)
|
||||
if not table_info.internal_name:
|
||||
# if table internal name is missing, table is not actually created
|
||||
# just remove the table_info entry for the table and
|
||||
# send notification
|
||||
LOG.info(("Table '{}' with tenant id '{}', id '{}' does not have "
|
||||
"valid internal name. Unable or no need to delete.").
|
||||
format(table_info.name, context.tenant, table_info.id))
|
||||
self._table_info_repo.delete(context, table_info.name)
|
||||
|
||||
self._notifier.info(
|
||||
context,
|
||||
notifier.EVENT_TYPE_TABLE_DELETE_END,
|
||||
table_info.name)
|
||||
else:
|
||||
self._do_delete_table(context, table_info)
|
||||
|
||||
return models.TableMeta(
|
||||
table_info.id,
|
||||
|
|
|
@ -100,6 +100,7 @@ class AsyncStorageManagerTestCase(unittest.TestCase):
|
|||
id = None
|
||||
schema = None
|
||||
creation_date_time = None
|
||||
internal_name = 'fake'
|
||||
|
||||
mock_table_info_repo = mock.Mock()
|
||||
mock_table_info_repo.get.return_value = FakeTableInfo()
|
||||
|
@ -136,3 +137,151 @@ class AsyncStorageManagerTestCase(unittest.TestCase):
|
|||
|
||||
# delete method of mock_table_info_repo has been called
|
||||
self.assertTrue(mock_table_info_repo.delete.called)
|
||||
|
||||
@mock.patch('magnetodb.storage.table_info_repo')
|
||||
def test_delete_table_create_or_delete_failed(self, mock_table_info_repo):
|
||||
context = mock.Mock(tenant='fake_tenant')
|
||||
table_name = 'fake_table'
|
||||
|
||||
mock_storage_driver = mock.Mock()
|
||||
mock_storage_driver.delete_table.return_value = True
|
||||
|
||||
class FakeTableInfoCreateFailed:
|
||||
status = models.TableMeta.TABLE_STATUS_CREATE_FAILED
|
||||
name = table_name
|
||||
in_use = False
|
||||
id = None
|
||||
schema = None
|
||||
creation_date_time = None
|
||||
internal_name = None
|
||||
|
||||
mock_table_info_repo = mock.Mock()
|
||||
mock_table_info_repo.get.return_value = FakeTableInfoCreateFailed()
|
||||
|
||||
storage_manager = async_simple_impl.AsyncSimpleStorageManager(
|
||||
mock_storage_driver,
|
||||
mock_table_info_repo
|
||||
)
|
||||
storage_manager.delete_table(context, table_name)
|
||||
|
||||
table_info_update_args_list = (
|
||||
mock_table_info_repo.update.call_args_list
|
||||
)
|
||||
|
||||
# called once, length of call_args_list indicates number of calls
|
||||
self.assertEqual(1, len(table_info_update_args_list))
|
||||
|
||||
self.assertEqual(2, len(table_info_update_args_list[0]))
|
||||
|
||||
# tuple of Mock, TableInfo, and status list
|
||||
self.assertEqual(3, len(table_info_update_args_list[0][0]))
|
||||
|
||||
# TableInfo status should be deleting
|
||||
self.assertEqual(models.TableMeta.TABLE_STATUS_DELETING,
|
||||
table_info_update_args_list[0][0][1].status)
|
||||
|
||||
for i in range(10):
|
||||
if mock_table_info_repo.delete.called:
|
||||
# delete_table method of mock_storage_driver should not
|
||||
# have been called since table does not actually exist
|
||||
self.assertFalse(mock_storage_driver.delete_table.called)
|
||||
break
|
||||
else:
|
||||
time.sleep(1)
|
||||
|
||||
# delete method of mock_table_info_repo has been called
|
||||
self.assertTrue(mock_table_info_repo.delete.called)
|
||||
|
||||
class FakeTableInfoDeleteFailedTableNotExist:
|
||||
status = models.TableMeta.TABLE_STATUS_DELETE_FAILED
|
||||
name = table_name
|
||||
in_use = False
|
||||
id = None
|
||||
schema = None
|
||||
creation_date_time = None
|
||||
internal_name = None
|
||||
|
||||
mock_table_info_repo = mock.Mock()
|
||||
mock_table_info_repo.get.return_value = (
|
||||
FakeTableInfoDeleteFailedTableNotExist())
|
||||
|
||||
storage_manager = async_simple_impl.AsyncSimpleStorageManager(
|
||||
mock_storage_driver,
|
||||
mock_table_info_repo
|
||||
)
|
||||
storage_manager.delete_table(context, table_name)
|
||||
|
||||
table_info_update_args_list = (
|
||||
mock_table_info_repo.update.call_args_list
|
||||
)
|
||||
|
||||
# called once, length of call_args_list indicates number of calls
|
||||
self.assertEqual(1, len(table_info_update_args_list))
|
||||
|
||||
self.assertEqual(2, len(table_info_update_args_list[0]))
|
||||
|
||||
# tuple of Mock, TableInfo, and status list
|
||||
self.assertEqual(3, len(table_info_update_args_list[0][0]))
|
||||
|
||||
# TableInfo status should be deleting
|
||||
self.assertEqual(models.TableMeta.TABLE_STATUS_DELETING,
|
||||
table_info_update_args_list[0][0][1].status)
|
||||
|
||||
for i in range(10):
|
||||
if mock_table_info_repo.delete.called:
|
||||
# delete_table method of mock_storage_driver should not
|
||||
# have been called since table does not actually exist
|
||||
self.assertFalse(mock_storage_driver.delete_table.called)
|
||||
break
|
||||
else:
|
||||
time.sleep(1)
|
||||
|
||||
# delete method of mock_table_info_repo has been called
|
||||
self.assertTrue(mock_table_info_repo.delete.called)
|
||||
|
||||
class FakeTableInfoDeleteFailedButTableExist:
|
||||
status = models.TableMeta.TABLE_STATUS_DELETE_FAILED
|
||||
name = table_name
|
||||
in_use = False
|
||||
id = None
|
||||
schema = None
|
||||
creation_date_time = None
|
||||
internal_name = 'fake'
|
||||
|
||||
mock_table_info_repo = mock.Mock()
|
||||
mock_table_info_repo.get.return_value = (
|
||||
FakeTableInfoDeleteFailedButTableExist())
|
||||
|
||||
storage_manager = async_simple_impl.AsyncSimpleStorageManager(
|
||||
mock_storage_driver,
|
||||
mock_table_info_repo
|
||||
)
|
||||
storage_manager.delete_table(context, table_name)
|
||||
|
||||
table_info_update_args_list = (
|
||||
mock_table_info_repo.update.call_args_list
|
||||
)
|
||||
|
||||
# called once, length of call_args_list indicates number of calls
|
||||
self.assertEqual(1, len(table_info_update_args_list))
|
||||
|
||||
self.assertEqual(2, len(table_info_update_args_list[0]))
|
||||
|
||||
# tuple of Mock, TableInfo, and status list
|
||||
self.assertEqual(3, len(table_info_update_args_list[0][0]))
|
||||
|
||||
# TableInfo status should be deleting
|
||||
self.assertEqual(models.TableMeta.TABLE_STATUS_DELETING,
|
||||
table_info_update_args_list[0][0][1].status)
|
||||
|
||||
for i in range(10):
|
||||
if mock_table_info_repo.delete.called:
|
||||
# delete_table method of mock_storage_driver should
|
||||
# have been called because table exists
|
||||
self.assertTrue(mock_storage_driver.delete_table.called)
|
||||
break
|
||||
else:
|
||||
time.sleep(1)
|
||||
|
||||
# delete method of mock_table_info_repo has been called
|
||||
self.assertTrue(mock_table_info_repo.delete.called)
|
||||
|
|
|
@ -101,6 +101,7 @@ class TestNotifyStorageManager(test_notification.TestNotify):
|
|||
id = None
|
||||
schema = None
|
||||
creation_date_time = None
|
||||
internal_name = None
|
||||
|
||||
mock_table_info_repo = mock.Mock()
|
||||
mock_table_info_repo.get.return_value = FakeTableInfo()
|
||||
|
|
Loading…
Reference in New Issue