Merge "Ensure instance files are deleted when using multiple CSVs" into stable/ocata

This commit is contained in:
Jenkins 2017-04-25 16:04:02 +00:00 committed by Gerrit Code Review
commit cef16d8db8
2 changed files with 36 additions and 10 deletions

View File

@ -740,7 +740,7 @@ class VMOps(object):
self._pathutils.remove(configdrive_path)
@serialconsoleops.instance_synchronized
def _delete_disk_files(self, instance_name):
def _delete_disk_files(self, instance_name, instance_path=None):
# We want to avoid the situation in which serial console workers
# are started while we perform this operation, preventing us from
# deleting the instance log files (bug #1556189). This can happen
@ -748,14 +748,23 @@ class VMOps(object):
#
# The unsynchronized method is being used to avoid a deadlock.
self._serial_console_ops.stop_console_handler_unsync(instance_name)
self._pathutils.get_instance_dir(instance_name,
create_dir=False,
remove_dir=True)
# This may be a 'non-default' location.
if not instance_path:
instance_path = self._pathutils.get_instance_dir(instance_name)
self._pathutils.check_remove_dir(instance_path)
def destroy(self, instance, network_info=None, block_device_info=None,
destroy_disks=True):
instance_name = instance.name
LOG.info(_LI("Got request to destroy instance"), instance=instance)
# Get the instance folder before destroying it. In some cases,
# we won't be able to retrieve it otherwise.
instance_path = self._pathutils.get_instance_dir(instance.name,
create_dir=False)
try:
if self._vmutils.vm_exists(instance_name):
@ -770,7 +779,7 @@ class VMOps(object):
LOG.debug("Instance not found", instance=instance)
if destroy_disks:
self._delete_disk_files(instance_name)
self._delete_disk_files(instance_name, instance_path)
except Exception:
with excutils.save_and_reraise_exception():
LOG.exception(_LE('Failed to destroy instance: %s'),

View File

@ -76,6 +76,7 @@ class VMOpsTestCase(test_base.HyperVBaseTestCase):
self._vmops._serial_console_ops = mock.MagicMock()
self._vmops._block_dev_man = mock.MagicMock()
self._vmops._vif_driver = mock.MagicMock()
self._pathutils = self._vmops._pathutils
def test_list_instances(self):
mock_instance = mock.MagicMock()
@ -1139,15 +1140,27 @@ class VMOpsTestCase(test_base.HyperVBaseTestCase):
self._vmops._pathutils.remove.assert_called_once_with(
mock.sentinel.configdrive_path)
def test_delete_disk_files(self):
@ddt.data(None, mock.sentinel.instance_path)
def test_delete_disk_files(self, passed_instance_path):
mock_instance = fake_instance.fake_instance_obj(self.context)
self._vmops._delete_disk_files(mock_instance.name)
self._vmops._delete_disk_files(mock_instance.name,
passed_instance_path)
stop_console_handler = (
self._vmops._serial_console_ops.stop_console_handler_unsync)
stop_console_handler.assert_called_once_with(mock_instance.name)
self._vmops._pathutils.get_instance_dir.assert_called_once_with(
mock_instance.name, create_dir=False, remove_dir=True)
if passed_instance_path:
self.assertFalse(self._vmops._pathutils.get_instance_dir.called)
else:
self._pathutils.get_instance_dir.assert_called_once_with(
mock_instance.name)
exp_inst_path = (passed_instance_path or
self._pathutils.get_instance_dir.return_value)
self._pathutils.check_remove_dir.assert_called_once_with(
exp_inst_path)
@mock.patch('hyperv.nova.volumeops.VolumeOps.disconnect_volumes')
@mock.patch('hyperv.nova.vmops.VMOps._delete_disk_files')
@ -1162,6 +1175,9 @@ class VMOpsTestCase(test_base.HyperVBaseTestCase):
block_device_info=mock.sentinel.FAKE_BD_INFO,
network_info=mock.sentinel.fake_network_info)
self._pathutils.get_instance_dir.assert_called_once_with(
mock_instance.name,
create_dir=False)
self._vmops._vmutils.vm_exists.assert_called_with(
mock_instance.name)
mock_power_off.assert_called_once_with(mock_instance)
@ -1172,7 +1188,8 @@ class VMOpsTestCase(test_base.HyperVBaseTestCase):
mock_disconnect_volumes.assert_called_once_with(
mock.sentinel.FAKE_BD_INFO)
mock_delete_disk_files.assert_called_once_with(
mock_instance.name)
mock_instance.name,
self._pathutils.get_instance_dir.return_value)
def test_destroy_inexistent_instance(self):
mock_instance = fake_instance.fake_instance_obj(self.context)