diff options
| author | Stanislaw Pitucha <stanislaw.pitucha@hp.com> | 2013-03-14 18:37:35 +0000 |
|---|---|---|
| committer | Devananda van der Veen <devananda.vdv@gmail.com> | 2013-04-03 07:32:44 -0700 |
| commit | 306046c7d5c20454035fcea22ce3efeac1d11cfc (patch) | |
| tree | 182fcf7c7478342a1b14ebb3255d6b7e816fd379 | |
| parent | 9df61c0b06dd81f34d97fbc02030f92928e21a78 (diff) | |
After migrate, catch and remove deleted instances
On the host init, starting with a deleted instance which has been
previously evacuated from the host results in an InstanceNotFound
exception. Catch and log this, and then call driver.destroy() so
that the hypervisor driver can clean up the deleted instance.
If we don't do this during host init, it will cause problems during
periodic tasks.
Fixes bug 1155152
Co-authored-by: Devananda van der Veen <devananda.vdv@gmail.com>
Change-Id: I979a698b8e739b9335f37b81e789285f91977a8e
| -rwxr-xr-x | nova/compute/manager.py | 22 | ||||
| -rw-r--r-- | nova/tests/compute/test_compute.py | 50 |
2 files changed, 67 insertions, 5 deletions
diff --git a/nova/compute/manager.py b/nova/compute/manager.py index 0c720c4ce..ca924fd12 100755 --- a/nova/compute/manager.py +++ b/nova/compute/manager.py @@ -434,13 +434,25 @@ class ComputeManager(manager.SchedulerDependentManager): '%(instance_host)s) is not equal to our ' 'host (%(our_host)s).'), locals(), instance=instance) - network_info = self._get_instance_nw_info(context, instance) - bdi = self._get_instance_volume_block_device_info(context, - instance) + # TODO(deva): detect if instance's disk is shared or local, + # and destroy if it is local. + destroy_disks = False + try: + network_info = self._get_instance_nw_info(context, + instance) + bdi = self._get_instance_volume_block_device_info(context, + instance) + except exception.InstanceNotFound: + network_info = network_model.NetworkInfo() + bdi = {} + LOG.info(_('Instance has been marked deleted already, ' + 'removing it from the hypervisor.'), + instance=instance) + # always destroy disks if the instance was deleted + destroy_disks = True self.driver.destroy(instance, self._legacy_nw_info(network_info), - bdi, - False) + bdi, destroy_disks) def _init_instance(self, context, instance): '''Initialize this instance during service init.''' diff --git a/nova/tests/compute/test_compute.py b/nova/tests/compute/test_compute.py index 3fdd79731..ce1857730 100644 --- a/nova/tests/compute/test_compute.py +++ b/nova/tests/compute/test_compute.py @@ -3822,6 +3822,56 @@ class ComputeTestCase(BaseTestCase): self.mox.VerifyAll() self.mox.UnsetStubs() + def test_init_host_with_deleted_migration(self): + our_host = self.compute.host + not_our_host = 'not-' + our_host + fake_context = 'fake-context' + + deleted_instance = { + 'name': 'fake-name', + 'host': not_our_host, + 'uuid': 'fake-uuid', + } + + self.mox.StubOutWithMock(self.compute.driver, 'init_host') + self.mox.StubOutWithMock(self.compute.driver, 'destroy') + self.mox.StubOutWithMock(self.compute.conductor_api, + 'instance_get_all_by_host') + self.mox.StubOutWithMock(context, 'get_admin_context') + self.mox.StubOutWithMock(self.compute, 'init_virt_events') + self.mox.StubOutWithMock(self.compute, '_get_instances_on_driver') + self.mox.StubOutWithMock(self.compute, '_init_instance') + self.mox.StubOutWithMock(self.compute, '_report_driver_status') + self.mox.StubOutWithMock(self.compute, 'publish_service_capabilities') + self.mox.StubOutWithMock(self.compute, '_get_instance_nw_info') + + self.compute.driver.init_host(host=our_host) + context.get_admin_context().AndReturn(fake_context) + self.compute.conductor_api.instance_get_all_by_host( + fake_context, our_host).AndReturn([]) + self.compute.init_virt_events() + + # simulate failed instance + self.compute._get_instances_on_driver(fake_context).AndReturn([ + deleted_instance]) + self.compute._get_instance_nw_info(fake_context, deleted_instance + ).AndRaise(exception.InstanceNotFound( + instance_id=deleted_instance['uuid'])) + # ensure driver.destroy is called so that driver may + # clean up any dangling files + self.compute.driver.destroy(deleted_instance, + mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg()) + + self.compute._report_driver_status(fake_context) + self.compute.publish_service_capabilities(fake_context) + + self.mox.ReplayAll() + self.compute.init_host() + # tearDown() uses context.get_admin_context(), so we have + # to do the verification here and unstub it. + self.mox.VerifyAll() + self.mox.UnsetStubs() + def test_init_instance_failed_resume_sets_error(self): instance = { 'uuid': 'fake-uuid', |
