diff options
author | Ivaylo Mitev <imitev@vmware.com> | 2020-05-08 10:59:10 -0700 |
---|---|---|
committer | Ivaylo Mitev <imitev@vmware.com> | 2020-05-27 07:20:35 -0700 |
commit | 20bc961a4c81dac6f92e971332447f71167edab3 (patch) | |
tree | 2e8cc429df51ed5f13485f8aeed7f07c25621eaa | |
parent | af6d26cee1a204d05c40ef9f8c5ac269d52a7e15 (diff) | |
download | oslo-vmware-20bc961a4c81dac6f92e971332447f71167edab3.tar.gz |
Validation of VMDK upload completion
Validate the completion of VMDK upload in ImportVApp. Otherwise, an
incomplete upload is falsely marked as successful which results in
corrupted VM.
Change-Id: I0608afd31daf95b564d3fc32028401d4aa526055
-rw-r--r-- | oslo_vmware/rw_handles.py | 17 | ||||
-rw-r--r-- | oslo_vmware/tests/test_rw_handles.py | 25 | ||||
-rw-r--r-- | releasenotes/notes/vmdk-transfer-validation-014d28cc9430e51b.yaml | 5 |
3 files changed, 45 insertions, 2 deletions
diff --git a/oslo_vmware/rw_handles.py b/oslo_vmware/rw_handles.py index b869e10..e0dfc7c 100644 --- a/oslo_vmware/rw_handles.py +++ b/oslo_vmware/rw_handles.py @@ -353,7 +353,13 @@ class VmdkHandle(FileHandle): LOG.debug("Lease for %(url)s is in state: %(state)s.", {'url': self._url, 'state': state}) - if state == 'ready': + if self._get_progress() < 100: + LOG.error("Aborting lease for %s due to incomplete transfer.", + self._url) + self._session.invoke_api(self._session.vim, + 'HttpNfcLeaseAbort', + self._lease) + elif state == 'ready': LOG.debug("Releasing lease for %s.", self._url) self._session.invoke_api(self._session.vim, 'HttpNfcLeaseComplete', @@ -506,7 +512,14 @@ class VmdkWriteHandle(VmdkHandle): super(VmdkWriteHandle, self).__init__(session, lease, url, self._conn) def get_imported_vm(self): - """"Get managed object reference of the VM created for import.""" + """"Get managed object reference of the VM created for import. + + :raises: VimException + """ + if self._get_progress() < 100: + excep_msg = _("Incomplete VMDK upload to %s.") % self._url + LOG.exception(excep_msg) + raise exceptions.ImageTransferException(excep_msg) return self._vm_ref def tell(self): diff --git a/oslo_vmware/tests/test_rw_handles.py b/oslo_vmware/tests/test_rw_handles.py index 1301bb7..d6ef43d 100644 --- a/oslo_vmware/tests/test_rw_handles.py +++ b/oslo_vmware/tests/test_rw_handles.py @@ -171,6 +171,18 @@ class VmdkHandleTest(base.TestCase): self.assertRaises(IOError, handle.fileno) + def test_release_lease_incomplete_transfer(self): + session = mock.Mock() + handle = rw_handles.VmdkHandle(session, None, 'fake-url', None) + + handle._get_progress = mock.Mock(return_value=99) + session.invoke_api = mock.Mock() + handle._release_lease() + + session.invoke_api.assert_called_with(handle._session.vim, + 'HttpNfcLeaseAbort', + handle._lease) + class VmdkWriteHandleTest(base.TestCase): """Tests for VmdkWriteHandle.""" @@ -276,9 +288,21 @@ class VmdkWriteHandleTest(base.TestCase): session.invoke_api = mock.Mock( side_effect=session_invoke_api_side_effect) + handle._get_progress = mock.Mock(return_value=100) handle.close() self.assertEqual(2, session.invoke_api.call_count) + def test_get_vm_incomplete_transfer(self): + session = self._create_mock_session() + handle = rw_handles.VmdkWriteHandle(session, '10.1.2.3', 443, 'rp-1', + 'folder-1', None, 100) + + handle._get_progress = mock.Mock(return_value=99) + session.invoke_api = mock.Mock() + + self.assertRaises(exceptions.ImageTransferException, + handle.get_imported_vm) + class VmdkReadHandleTest(base.TestCase): """Tests for VmdkReadHandle.""" @@ -390,6 +414,7 @@ class VmdkReadHandleTest(base.TestCase): session.invoke_api = mock.Mock( side_effect=session_invoke_api_side_effect) + handle._get_progress = mock.Mock(return_value=100) handle.close() self.assertEqual(2, session.invoke_api.call_count) diff --git a/releasenotes/notes/vmdk-transfer-validation-014d28cc9430e51b.yaml b/releasenotes/notes/vmdk-transfer-validation-014d28cc9430e51b.yaml new file mode 100644 index 0000000..dc96cc7 --- /dev/null +++ b/releasenotes/notes/vmdk-transfer-validation-014d28cc9430e51b.yaml @@ -0,0 +1,5 @@ +--- +fixes: + - | + Incomplete VMDK upload during ImportVApp is falsely marked as successful + leading to a corrupted VM. |