cloudstack/test/integration/component/maint/testpath_disablestoragepool.py
John Bampton def7ce655d
Fix spelling (#6898)
Co-authored-by: davidjumani <dj.davidjumani1994@gmail.com>
2022-12-13 14:58:14 +01:00

1623 lines
69 KiB
Python

# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
"""Utilities functions
"""
# All tests inherit from cloudstack TestCase
from marvin.cloudstackTestCase import cloudstackTestCase
from marvin.cloudstackTestCase import cloudstackTestCase
import unittest
from marvin.codes import FAILED, PASS
from marvin.lib.base import (Account,
VirtualMachine,
ServiceOffering,
User,
DiskOffering,
Volume,
Template,
VmSnapshot,
StoragePool,
Host,
Capacities)
from marvin.lib.utils import cleanup_resources, validateList
from marvin.lib.common import (get_zone,
get_domain,
list_clusters,
get_template,
list_volumes,
list_virtual_machines)
from nose.plugins.attrib import attr
from ddt import ddt, data
def verify_vm_state(self, vmid, state):
list_vm = list_virtual_machines(self.userapiclient,
account=self.account.name,
domainid=self.account.domainid,
id=vmid)
self.assertEqual(
validateList(list_vm)[0],
PASS,
'Check List vm response for vmid: %s' %
vmid)
self.assertGreater(
len(list_vm),
0,
'Check the list vm response for vm id: %s' %
vmid)
vm = list_vm[0]
self.assertEqual(
vm.id,
str(vmid),
'Vm deployed is different from the test')
self.assertEqual(vm.state, state, 'VM is not in %s state' % state)
self.debug('VM is in is %s state' % state)
def verify_pool_state(self, poolid, state):
list_storage_pool_response = StoragePool.list(
self.userapiclient, id=poolid)
self.assertGreater(len(list_storage_pool_response), 0,
'Check list pool response is greater than 0')
self.assertEqual(
list_storage_pool_response[0].state,
state,
'Storage pool is not in %s state' %
state)
def verify_vm_storage_pool(self, vmid, storageid):
root_volume = Volume.list(
self.userapiclient,
virtualmachineid=vmid,
type='ROOT')[0]
list_volume = Volume.list(self.userapiclient, id=root_volume.id)
self.assertEqual(
list_volume[0].storageid,
storageid,
'check list volume response for Storage id: % s ' %
storageid)
@ddt
class TestPathDisableStorage_Basic(cloudstackTestCase):
"""
# Tests in this path requires to be run independently
# ( not to be run in parallel with any other tests since it involves disabling/enabling storage pools \
and may cause unexpected failures in other tests
# The test also requires to have 2 Cluster-wide and 2 zone-wide storage pools available in the setup.
# For running the tests on local storage, ensure there are 2 local storage pools set up on each host
"""
@classmethod
def setUpClass(cls):
testClient = super(
TestPathDisableStorage_Basic,
cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient)
cls.testdata['mode'] = cls.zone.networktype
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata['ostype'])
cls.testdata['template']['ostypeid'] = cls.template.ostypeid
if cls.template == FAILED:
cls.fail(
'get_template() failed to return template with description %s'
% cls.testdata['ostype'])
cls._cleanup = []
cls.disabled_list = []
cls.testdata['template_2']['zoneid'] = cls.zone.id
cls.testdata['template_2']['ostypeid'] = cls.template.ostypeid
cls.hypervisor = testClient.getHypervisorInfo()
try:
cls.debug('Creating account')
cls.account = Account.create(cls.apiclient,
cls.testdata['account'],
admin=True
)
cls._cleanup.append(cls.account)
except Exception as e:
cls.tearDownClass()
raise e
# Create shared storage offerings
cls.service_offering_shared = ServiceOffering.create(
cls.apiclient, cls.testdata['service_offering'])
cls._cleanup.append(cls.service_offering_shared)
cls.disk_offering_shared = DiskOffering.create(
cls.apiclient, cls.testdata['disk_offering'])
cls.resized_disk_offering = DiskOffering.create(
cls.apiclient, cls.testdata['resized_disk_offering'])
cls._cleanup.append(cls.disk_offering_shared)
# Create offerings for local storage if local storage is enabled
if cls.zone.localstorageenabled:
cls.testdata["service_offerings"]["tiny"]["storagetype"] = 'local'
cls.service_offering_local = ServiceOffering.create(
cls.apiclient, cls.testdata["service_offerings"]["tiny"])
cls._cleanup.append(cls.service_offering_local)
cls.testdata["disk_offering"]["storagetype"] = 'local'
cls.disk_offering_local = DiskOffering.create(
cls.apiclient, cls.testdata["disk_offering"])
cls._cleanup.append(cls.disk_offering_local)
cls.testdata["disk_offering"]["storagetype"] = ' '
cls.testdata["service_offerings"]["tiny"]["storagetype"] = ' '
else:
cls.debug("No local storage found")
cls.userapiclient = testClient.getUserApiClient(
UserName=cls.account.name, DomainName=cls.account.domain)
response = User.login(cls.userapiclient,
username=cls.account.name,
password=cls.testdata['account']['password']
)
assert response.sessionkey is not None
@classmethod
def tearDownClass(cls):
try:
cleanup_resources(cls.apiclient, cls._cleanup)
except Exception as e:
raise Exception('Warning:Exception during cleanup: %s' % e)
def setUp(self):
self.apiclient = self.testClient.getApiClient()
self.cleanup = []
def tearDown(self):
if self.disabled_list:
for poolid in self.disabled_list:
if StoragePool.list(
self.userapiclient,
id=poolid)[0].state != 'Up':
try:
StoragePool.update(
self.userapiclient, id=poolid, enabled=True)
self.debug('Enabling: % s ' % poolid)
except Exception as e:
self.fail("Couldn't enable storage % s" % id)
try:
cleanup_resources(self.apiclient, self.cleanup)
except Exception as e:
self.fail('Warning: Exception during cleanup : %s' % e)
@data('host', 'CLUSTER', 'ZONE')
@attr(tags=['advanced', 'advancedsg', 'basic'], required_hardware='false')
def test_01_disable_enable_pool(self, value):
"""
Test Steps:
=========
1. Deploy 2 VMs
2. Stop VM2
3. Disable storage pool SP1
4. Try to deploy a new VM, should fail
5. Start VM2 which was stopped, should run from same pool
6. Remove disabled Storage pool SP1, should fail
7. Enable storage pool SP1
8. Deploy new VM, VM4 - should succeed
9. Create and attach new disk to VM4
10. Disable storage pool SP1 again and enable new pool
11. Deploy new VM, VM5 - should succeed
12. Stop VM1 which is running from disabled pool
13. Migrate ROOT volume of VM1 to another enabled storage pool - should succeed
14. findStoragePoolsforMigration should not list the disabled pool
"""
# Choose appropriate service offering depending on the scope the test
# is being run on
self.disabled_list = []
if value == 'CLUSTER':
other_scope = 'ZONE'
self.service_offering = self.service_offering_shared
self.disk_offering = self.disk_offering_shared
elif value == 'ZONE':
other_scope = 'CLUSTER'
self.service_offering = self.service_offering_shared
self.disk_offering = self.disk_offering_shared
elif value == 'host':
# local storage
other_scope = None
if self.zone.localstorageenabled:
self.service_offering = self.service_offering_local
self.disk_offering = self.disk_offering_local
else:
self.skipTest("Local storage not enabled")
# Keep only one pool active and disable the rest
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope=value)
if self.list_storage:
count_st_pools = len(self.list_storage)
else:
count_st_pools = 0
self.disabled_pool_1 = None
if count_st_pools > 1:
self.debug(
'Found % s storage pools, keeping one and disabling rest' %
count_st_pools)
for pool in self.list_storage[1:]:
self.disabled_pool_1 = self.list_storage[1]
if pool.state == 'Up':
self.debug('Trying to disable storage %s' % pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
raise e
elif count_st_pools == 1:
self.debug(
'Only one % s wide storage found - will not be able to complete all tests' %
value)
else:
self.skipTest('No % s storage pools found' % value)
except Exception as e:
raise e
# Disable the other scope shared storage pools while we are testing on
# one - applicable for only shared storage
if value != 'host':
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope=other_scope)
if self.list_storage:
for pool in self.list_storage:
if pool.state == 'Up':
self.debug(
'Trying to disable storage % s' %
pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
self.fail(
"Couldn't disable storage % s" % pool.id)
else:
self.debug('No % s wide storage pools found' % other_scope)
except Exception as e:
raise e
# Step 1: Deploy 2 VMs
self.virtual_machine_1 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
self.virtual_machine_2 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_2.id, 'Running')
# Step 2: Keep one VM in stopped state while other keeps running
try:
self.debug('Step 2: Stopping one of the VMs')
self.virtual_machine_2.stop(self.userapiclient)
verify_vm_state(self, self.virtual_machine_2.id, 'Stopped')
except Exception as e:
self.fail('Step 2: Failed to stop VM: %s' % e)
# Step 3: Disable the Storage Pool, verify VMs are in same state as
# before
self.storage_pools_list = StoragePool.list(
self.userapiclient, scope=value, state='Up')
self.storage_pool_1 = self.storage_pools_list[0]
try:
self.debug(
'Step 3: Disabling Storage Pool: %s' %
self.storage_pool_1.id)
StoragePool.update(
self.userapiclient,
id=self.storage_pool_1.id,
enabled=False)
except Exception as e:
self.debug("Step 3: Couldn't disable pool %s" % e)
verify_pool_state(self, self.storage_pool_1.id, 'Disabled')
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
verify_vm_state(self, self.virtual_machine_2.id, 'Stopped')
# Step 4: Deploying new VM on disabled pool should fail
self.debug(
'Step 4: Trying to deploy VM on disabled storage - should fail')
with self.assertRaises(Exception):
VirtualMachine.create(self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
# Step 5: Should be able to start VM on disabled pool
try:
self.virtual_machine_2.start(self.userapiclient)
verify_vm_state(self, self.virtual_machine_2.id, 'Running')
verify_vm_storage_pool(
self,
self.virtual_machine_2.id,
self.storage_pool_1.id)
except Exception as e:
self.fail('Step 5: Failed to start VM: %s' % e)
# Step 6: Removing disabled pool should fail
self.debug('Step 6: Trying to remove disabled storage pool')
with self.assertRaises(Exception):
StoragePool.delete(self.userapiclient, self.storage_pool_1.id)
# Step 7: Enable Storage pool
try:
self.debug(
'Step 7: Enabling Storage Pool: %s' %
self.storage_pool_1.id)
StoragePool.update(
self.userapiclient,
id=self.storage_pool_1.id,
enabled=True)
except Exception as e:
self.debug("Step 7: Couldn't enable pool %s" % e)
verify_pool_state(self, self.storage_pool_1.id, 'Up')
# Step 8: Deploy a VM on the pool
self.virtual_machine_3 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_3.id, 'Running')
if self.hypervisor.lower() == 'lxc':
self.skipTest("Not running rest of tests in lxc")
# Step 9: Create and attach new disk to VM
self.volume = Volume.create(self.userapiclient,
services=self.testdata['volume'],
diskofferingid=self.disk_offering.id,
zoneid=self.zone.id)
list_volume = Volume.list(
self.userapiclient,
id=self.volume.id,
accountid=self.account.name,
domainid=self.account.domainid)
self.assertEqual(
validateList(list_volume)[0],
PASS,
'Step 9: Check List volume response for volume %s' %
self.volume.id)
self.assertEqual(
list_volume[0].id,
self.volume.id,
'Step 9: check list volume response for volume id: %s' %
self.volume.id)
self.debug(
'Step 9: volume id %s got created successfully' %
list_volume[0].id)
self.virtual_machine_3.attach_volume(self.userapiclient, self.volume)
list_volume = Volume.list(self.userapiclient, id=self.volume.id)
self.assertEqual(
list_volume[0].virtualmachineid,
self.virtual_machine_3.id,
'Step 9: Check if volume state (attached) is reflected')
self.debug(
'Step 9: volume id:%s successfully attached to vm id%s' %
(self.volume.id, self.virtual_machine_3.id))
if self.disabled_pool_1:
newpoolid = self.disabled_pool_1.id
else:
self.skipTest(
'Step 9: Could not find a second storage pool to complete the remaining tests')
# Step 10: Disable storage pool SP1 again and enable new pool
try:
StoragePool.update(self.userapiclient, id=newpoolid, enabled=True)
except Exception as e:
self.fail('Step 10: Enable storage pool %s' % e, 'failed')
verify_pool_state(self, newpoolid, 'Up')
try:
self.debug(
'Step 10: Disabling Storage Pool: %s' %
self.storage_pool_1.id)
StoragePool.update(
self.userapiclient,
id=self.storage_pool_1.id,
enabled=False)
self.disabled_list.append(self.storage_pool_1.id)
self.debug(
'Step 10: Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
self.debug("Step 10: Couldn't disable pool %s" % e)
verify_pool_state(self, self.storage_pool_1.id, 'Disabled')
# Step 11: Deploy new VM, VM5 - should succeed
self.virtual_machine_4 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_4.id, 'Running')
# Step 12: Stop VM1 which is running from disabled pool
self.virtual_machine_1.stop(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Stopped')
# Step 13: Migrate ROOT volume of VM1 to another enabled storage pool -
# should succeed
if value != 'host':
root_volume = Volume.list(
self.userapiclient,
virtualmachineid=self.virtual_machine_1.id,
type='ROOT')
try:
Volume.migrate(
self.userapiclient,
volumeid=root_volume[0].id,
storageid=newpoolid)
except Exception as e:
raise e
list_volume = list_volumes(
self.userapiclient, id=root_volume[0].id)
self.assertEqual(
isinstance(
list_volume,
list),
True,
'Step 13: Check list volumes response for valid list')
# Step 14: findStoragePoolsforMigration should not list the disabled
# pool
if value != 'host':
pools_for_migration = StoragePool.listForMigration(
self.userapiclient, id=root_volume[0].id)
self.debug(
'Step 14: List of pools suitable for migration: % s ' %
pools_for_migration)
if pools_for_migration:
if self.storage_pool_1 in pools_for_migration:
self.fail(
'Step 14: Storage pool % s is supposed to be disabled and not suitable for migration, \
but found in the list of pools suitable for migration' %
self.storage_pool_1.id)
@data('host', 'CLUSTER', 'ZONE')
@attr(tags=['advanced', 'advancedsg', 'basic'], required_hardware='false')
def test_02_vm_operations_on_disabled_pool(self, value):
"""
Test Steps:
=========
1. Deploy a VM and attach volume
2. Disable Storage
3. Create Template from root volume of the VM
4. Attach a new volume - should fail
5. Resize DATA disk to a higher value
6. Take VM Snapshot of the VM (for supported hypervisors)
7. Destroy the VM and immediately restore the VM
8. Enable a new storage pool
9. Re-install the VM with same template
10. Re-install the VM with the new template created earlier
11. Repeat tests with enabled pool, Attach new Volume to VM2
12. Resize disk to a higher value
13. Reboot the VM
14. Take VM Snapshot of the VM
15. Destroy the VM and immediately restore the VM
"""
# Choose appropriate service offering depending on the scope the test
# is being run on
self.disabled_list = []
if value == 'CLUSTER':
other_scope = 'ZONE'
self.service_offering = self.service_offering_shared
self.disk_offering = self.disk_offering_shared
elif value == 'ZONE':
other_scope = 'CLUSTER'
self.service_offering = self.service_offering_shared
self.disk_offering = self.disk_offering_shared
elif value == 'host':
# local storage
other_scope = None
if self.zone.localstorageenabled:
self.service_offering = self.service_offering_local
self.disk_offering = self.disk_offering_local
else:
self.skipTest("Local storage not enabled")
if self.hypervisor.lower() == 'lxc':
self.skipTest("Not running rest of tests in lxc")
# Keep one storage pool active and disable the rest
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope=value)
if self.list_storage:
count_st_pools = len(self.list_storage)
else:
count_st_pools = 0
self.disabled_pool_1 = None
if count_st_pools > 1:
self.debug(
'Found % s storage pools, keeping one and disabling rest' %
count_st_pools)
for pool in self.list_storage[1:]:
self.disabled_pool_1 = self.list_storage[1]
if pool.state == 'Up':
self.debug('Trying to disable storage %s' % pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
raise e
elif count_st_pools == 1:
self.debug(
'Only one % s wide storage found - will not be able to complete all tests' %
value)
else:
self.skipTest('No % s wide storage pools found' % value)
except Exception as e:
raise e
# Disable the other scope storage pools while we are testing on one
# scope - applicable for only shared storage
if value != 'host':
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope=other_scope)
if self.list_storage:
for pool in self.list_storage:
if pool.state == 'Up':
self.debug(
'Trying to disable storage % s' %
pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
self.fail(
"Couldn't disable storage % s" % pool.id)
else:
self.debug('No % s wide storage pools found' % other_scope)
except Exception as e:
raise e
# Step 1: Deploy a VM and attach data disk to one VM
self.virtual_machine_1 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
self.volume_1 = Volume.create(self.userapiclient,
services=self.testdata['volume'],
diskofferingid=self.disk_offering.id,
zoneid=self.zone.id)
self.virtual_machine_1.attach_volume(self.userapiclient, self.volume_1)
list_volume = Volume.list(self.userapiclient, id=self.volume_1.id)
self.assertEqual(
list_volume[0].virtualmachineid,
self.virtual_machine_1.id,
''
'Check if volume state (attached) is reflected')
self.debug(
'Step 1: volume id:%s successfully attached to vm id%s' %
(self.volume_1.id, self.virtual_machine_1.id))
# Step 2: Disable the storage pool
self.storage_pools_list = StoragePool.list(
self.userapiclient, scope=value, state='Up')
self.storage_pool_1 = self.storage_pools_list[0]
try:
self.debug(
'Step 2: Disabling Storage Pool: %s' %
self.storage_pool_1.id)
StoragePool.update(
self.userapiclient,
id=self.storage_pool_1.id,
enabled=False)
self.disabled_list.append(self.storage_pool_1.id)
except Exception as e:
self.debug("Step 2: Couldn't disable pool %s" % e)
verify_pool_state(self, self.storage_pool_1.id, 'Disabled')
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
# Step 3: Create Template from root volume of the VM
root_volume_1 = Volume.list(
self.userapiclient,
virtualmachineid=self.virtual_machine_1.id,
type='ROOT')[0]
self.virtual_machine_1.stop(self.userapiclient)
try:
template_2 = Template.create(self.userapiclient,
self.testdata['template_2'],
volumeid=root_volume_1.id,
account=self.account.name,
domainid=self.account.domainid)
self.cleanup.append(template_2)
self.debug('Step 3: Created template with ID: %s' % template_2.id)
list_template = Template.list(
self.userapiclient,
templatefilter='self',
id=template_2.id)
except Exception as e:
self.fail('Step 3: Template from volume failed')
# Step 4: Attach a new volume - should fail
self.volume_2 = Volume.create(self.userapiclient,
services=self.testdata['volume'],
diskofferingid=self.disk_offering.id,
zoneid=self.zone.id)
self.debug(
'Step 4: Trying to attach new volume to VM on disabled storage - should fail')
with self.assertRaises(Exception):
self.virtual_machine_1.attach_volume(
self.userapiclient, self.volume_2)
# Step 5: Resize DATA disk to a higher value for attached disk
try:
self.volume_1.resize(self.userapiclient,
diskofferingid=self.resized_disk_offering.id)
list_volume_1 = Volume.list(
self.userapiclient, id=self.volume_1.id)
self.assertEqual(
list_volume_1[0].diskofferingid,
self.resized_disk_offering.id,
'check list volume response for volume id: %s' %
self.volume_1.id)
self.debug(
'Step 5: volume id %s got resized successfully' %
list_volume_1[0].id)
except Exception as e:
self.fail('Step 5: Volume resize on disabled pool failed: % s' % e)
# Step 6: Take VM Snapshot
if self.hypervisor.lower() not in ('kvm', 'hyperv', 'lxc'):
try:
self.debug(
"Step 6: Taking VM Snapshot for vm id % s" %
self.virtual_machine_1.id)
vm_snapshot = VmSnapshot.create(self.userapiclient,
self.virtual_machine_1.id,
'false',
'TestSnapshot',
'Display Text')
self.assertEqual(
vm_snapshot.state,
'Ready',
'Check VM snapshot is ready')
except Exception as e:
self.fail(
'Step 6: VM Snapshot on disabled pool failed: % s' %
e)
if vm_snapshot:
self.debug('Step 6: Deleting Vm Snapshot')
VmSnapshot.deleteVMSnapshot(self.userapiclient, vm_snapshot.id)
# Step 7: Destroy VM and immediately restore the VM
self.debug(
"Step 7: Deleting and restoring the VM, should continue to run from same storage pool")
self.virtual_machine_1.delete(self.userapiclient, expunge=False)
self.virtual_machine_1.recover(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Stopped')
self.virtual_machine_1.start(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
verify_vm_storage_pool(
self,
self.virtual_machine_1.id,
self.storage_pool_1.id)
# Step 8: Enable new pool
if self.disabled_pool_1:
try:
newpoolid = self.disabled_pool_1.id
StoragePool.update(
self.userapiclient, id=newpoolid, enabled=True)
self.debug("Step 8: Enabling new pool % s " % newpoolid)
if newpoolid in self.disabled_list:
self.disabled_list.remove(newpoolid)
except Exception as e:
self.fail('Step 8: Enable storage pool %s' % e, 'failed')
else:
self.debug(
'Step 8: Could not find a second storage pool, so enabling the first storage pool and running the tests')
try:
self.debug(
'Step 8: Enabling Storage Pool: %s' %
self.storage_pool_1.id)
StoragePool.update(
self.userapiclient,
id=self.storage_pool_1.id,
enabled=True)
if self.storage_pool_1.id in self.disabled_list:
self.disabled_list.remove(self.storage_pool_1.id)
newpoolid = self.storage_pool_1.id
except Exception as e:
self.fail("Step 8: Couldn't enable pool %s" % e)
verify_pool_state(self, newpoolid, 'Up')
# Step 9: Re-install the VM with same template
if value != 'host':
self.debug("Step 9: Re-installing VM 1")
vm_restore = self.virtual_machine_1.restore(
self.userapiclient, templateid=self.template.id)
verify_vm_storage_pool(self, self.virtual_machine_1.id, newpoolid)
# Step 10 : Re-install VM with different template
self.debug("Step 10: re-installing VM with different template")
vm_restore = self.virtual_machine_1.restore(
self.userapiclient, templateid=template_2.id)
verify_vm_storage_pool(self, self.virtual_machine_1.id, newpoolid)
# Step 11: Repeat tests with enabled pool. Start with attach VM
if value != 'host':
self.debug("Step 11: Attach volume to VM")
self.virtual_machine_1.attach_volume(
self.userapiclient, self.volume_2)
list_volume_2 = Volume.list(
self.userapiclient, id=self.volume_2.id)
self.assertEqual(list_volume_2[0].virtualmachineid,
self.virtual_machine_1.id,
'Check if volume state (attached) is reflected')
self.debug(
'Step 11: volume id:% s successfully attached to vm id % s' %
(self.volume_2.id, self.virtual_machine_1.id))
# Step 12: Re-size Volume to higher disk offering
try:
self.virtual_machine_1.stop(self.userapiclient)
self.volume_2.resize(
self.userapiclient,
diskofferingid=self.resized_disk_offering.id)
list_volume_2 = Volume.list(
self.userapiclient, id=self.volume_2.id)
self.assertEqual(
list_volume_2[0].diskofferingid,
self.resized_disk_offering.id,
'check list volume response for volume id: %s' %
self.volume_2.id)
self.debug(
'Step 12: volume id %s got resized successfully' %
list_volume_2[0].id)
except Exception as e:
self.fail('Step 12: Failed to resize volume % s ' % e)
self.virtual_machine_1.start(self.userapiclient)
# Step 13: Reboot VM
self.virtual_machine_1.reboot(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
# Step 14: Take Snapshot of VM
if self.hypervisor.lower() not in ('kvm', 'hyperv', 'lxc'):
try:
vm_snapshot = VmSnapshot.create(
self.userapiclient,
self.virtual_machine_1.id,
'false',
'TestSnapshot2',
'Display Text')
self.assertEqual(
vm_snapshot.state,
'Ready',
'Check the snapshot of vm is ready!')
except Exception as e:
self.fail(
'Step 14: Snapshot failed post enabling new storage pool')
# Step 15: Delete and recover VM
self.debug("Step 15: Deleting and recovering VM")
self.virtual_machine_1.delete(self.userapiclient, expunge=False)
self.virtual_machine_1.recover(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Stopped')
self.virtual_machine_1.start(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
@ddt
class TestPathDisableStorage_Maint_Tags(cloudstackTestCase):
"""
# Tests in this path requires to be run independently
# Not to be run in parallel with any other tests since it involves disabling/enabling storage pools \
and may cause unexpected failures in other tests
# The test also requires to have 2 Cluster-wide and 2 zone-wide storage pools available in the setup.
# For running the tests on local storage, ensure there are 2 local storage pools set up on each host or different hosts
"""
@classmethod
def setUpClass(cls):
testClient = super(
TestPathDisableStorage_Maint_Tags,
cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient)
cls.testdata['mode'] = cls.zone.networktype
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata['ostype'])
cls.testdata['template']['ostypeid'] = cls.template.ostypeid
if cls.template == FAILED:
cls.fail(
'get_template() failed to return template with description %s' %
cls.testdata['ostype'])
cls._cleanup = []
cls.disabled_list = []
cls.maint_list = []
cls.testdata['template_2']['zoneid'] = cls.zone.id
cls.testdata['template_2']['ostypeid'] = cls.template.ostypeid
cls.hypervisor = testClient.getHypervisorInfo()
try:
cls.account = Account.create(cls.apiclient,
cls.testdata['account'],
admin=True)
cls.debug('Creating account')
cls._cleanup.append(cls.account)
# Create shared storage offerings
cls.service_offering_shared = ServiceOffering.create(
cls.apiclient, cls.testdata['service_offering'])
cls._cleanup.append(cls.service_offering_shared)
cls.disk_offering_shared = DiskOffering.create(
cls.apiclient, cls.testdata['disk_offering'])
cls.resized_disk_offering = DiskOffering.create(
cls.apiclient, cls.testdata['resized_disk_offering'])
cls._cleanup.append(cls.disk_offering_shared)
# Create offerings for local storage if local storage is enabled
if cls.zone.localstorageenabled:
cls.testdata["service_offerings"][
"tiny"]["storagetype"] = 'local'
cls.debug("Creating local storage offering")
cls.service_offering_local = ServiceOffering.create(
cls.apiclient, cls.testdata["service_offerings"]["tiny"])
cls._cleanup.append(cls.service_offering_local)
cls.testdata["disk_offering"]["storagetype"] = 'local'
cls.debug("Creating local storage disk offering")
cls.disk_offering_local = DiskOffering.create(
cls.apiclient, cls.testdata["disk_offering"])
cls._cleanup.append(cls.disk_offering_local)
cls.testdata["disk_offering"]["storagetype"] = ' '
cls.testdata["service_offerings"]["tiny"]["storagetype"] = ' '
else:
cls.debug("No local storage found")
cls.userapiclient = testClient.getUserApiClient(
UserName=cls.account.name, DomainName=cls.account.domain)
response = User.login(cls.userapiclient,
username=cls.account.name,
password=cls.testdata['account']['password'])
assert response.sessionkey is not None
except Exception as e:
cls.tearDownClass()
raise e
@classmethod
def tearDownClass(cls):
try:
cleanup_resources(cls.apiclient, cls._cleanup)
except Exception as e:
raise Exception('Warning:Exception during cleanup: %s' % e)
def setUp(self):
self.apiclient = self.testClient.getApiClient()
self.cleanup = []
def tearDown(self):
if self.disabled_list:
for poolid in self.disabled_list:
if StoragePool.list(self.userapiclient, id=poolid)[0].state == 'Disabled':
try:
StoragePool.update(
self.userapiclient, id=poolid, enabled=True)
self.debug('Enabling: % s ' % poolid)
except Exception as e:
self.fail("Couldn't enable storage % s" % id)
if self.maint_list:
for poolid in self.maint_list:
if StoragePool.list(self.userapiclient, id=poolid)[0].state == 'Maintenance':
try:
StoragePool.cancelMaintenance(
self.userapiclient, id=poolid)
self.debug(
'Cancelled Maintenance mode for % s' %
poolid)
except Exception as e:
self.fail(
"Couldn't cancel Maintenance mode for storage % s " %
poolid)
try:
cleanup_resources(self.apiclient, self.cleanup)
except Exception as e:
self.fail('Warning: Exception during cleanup : %s' % e)
@data('host', 'CLUSTER', 'ZONE')
@attr(tags=['advanced', 'advancedsg', 'basic'], required_hardware='false')
def test_01_maint_capacity_tags(self, value):
"""
Test Steps:
========
1. Deploy VM
2. Add storage to maintenance
3. Cancel Maintenance
4. Disable pool and then Start the VM - verify it runs off the same pool
5. Perform more VM operations - reboot
6. Add tags to pool
7. Create tagged offering with same tags
8. Enable pool
9. Deploy VM using the tagged offering
10. Disable storage pool again
11. Calculate current capacity used so far for the storage pool
12. Delete VM and check capacity is re-calculated in the disabled pool
13. Perform VM deploy - should fail since pool is disabled
14. Re-calculate Capacity, should not be altered
"""
# Choose appropriate service offering depending on the scope the test
# is being run on
self.disabled_list = []
if value == 'CLUSTER':
other_scope = 'ZONE'
self.service_offering = self.service_offering_shared
self.disk_offering = self.disk_offering_shared
elif value == 'ZONE':
other_scope = 'CLUSTER'
self.service_offering = self.service_offering_shared
self.disk_offering = self.disk_offering_shared
elif value == 'host':
# local storage
if self.zone.localstorageenabled:
other_scope = None
self.service_offering = self.service_offering_local
self.disk_offering = self.disk_offering_local
else:
self.skipTest("Local storage not enabled")
# Keep 2 storage pools active and disable the rest. If only one storage
# pool is present, then skip the test
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope=value)
count_st_pools = len(self.list_storage)
if count_st_pools <= 1:
raise unittest.SkipTest(
'Found 1 or less storage pools in % s wide scope- cannot proceed' %
value)
elif count_st_pools > 2:
for pool in self.list_storage[2:]:
if pool.state == 'Up':
self.debug('Trying to disable storage %s' % pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
raise e
elif count_st_pools == 2:
for pool in self.list_storage:
if pool.state != 'Up':
raise unittest.SkipTest(
'Found storage pool % s not in Up State.. cannot proceed' %
pool.id)
except Exception as e:
raise e
# Disable the other scope shared storage pools while we are testing on
# one - applicable for only shared storage
if value != 'host':
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope=other_scope)
if self.list_storage:
for pool in self.list_storage:
if pool.state == 'Up':
self.debug(
'Trying to disable storage % s' %
pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
self.fail(
"Couldn't disable storage % s" % pool.id)
else:
self.debug('No % s wide storage pools found' % other_scope)
except Exception as e:
raise e
self.debug("Step 1: Deploy VM")
self.virtual_machine_1 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
# Step 2: Add storage to Maintenance mode
self.debug("Step 2: Adding storage to maintenance mode ")
root_volume = Volume.list(
self.userapiclient,
virtualmachineid=self.virtual_machine_1.id,
type='ROOT')[0]
list_volume = Volume.list(self.userapiclient, id=root_volume.id)
storage_id = list_volume[0].storageid
try:
StoragePool.enableMaintenance(self.userapiclient, id=storage_id)
self.debug('Step 2: Added % s to Maintenance mode')
self.maint_list.append(storage_id)
except Exception as e:
self.fail(
'Step 2: Failed to add Storage pool % s to Maintenance mode' %
storage_id)
verify_vm_state(self, self.virtual_machine_1.id, 'Stopped')
# Step 3: Cancel maintenance mode
try:
StoragePool.cancelMaintenance(self.userapiclient, id=storage_id)
self.debug(
'Step 3: Cancelled Maintenance mode for % s' %
storage_id)
self.maint_list.remove(storage_id)
except Exception as e:
self.fail(
"Step 3: Couldn't cancel Maintenance mode for storage % s " %
storage_id)
# Step 4: Start the VM after disabling pool and verify it's running
# from same pool
try:
self.debug("Step 4: Starting VM after disabling pool")
self.list_storage = StoragePool.list(
self.userapiclient, id=storage_id)
if self.list_storage[0].state == 'Up':
StoragePool.update(
self.userapiclient,
id=storage_id,
enabled=False)
self.debug("Step 4: Disabled pool % s" % storage_id)
self.disabled_list.append(storage_id)
except Exception as e:
raise e
list_vm = list_virtual_machines(
self.userapiclient,
account=self.account.name,
domainid=self.account.domainid,
id=self.virtual_machine_1.id)
vm = list_vm[0]
if vm.state != 'Running':
self.virtual_machine_1.start(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
verify_vm_storage_pool(self, self.virtual_machine_1.id, storage_id)
# Step 5: Perform some VM operations - reboot
self.debug(
"Step 5: Performing reboot of VM % s" %
self.virtual_machine_1.id)
self.virtual_machine_1.reboot(self.userapiclient)
verify_vm_storage_pool(self, self.virtual_machine_1.id, storage_id)
# Step 6: Add tags to the storage pool
self.debug("Step 6: Adding tags to storage pool")
StoragePool.update(
self.userapiclient,
id=storage_id,
tags='disable_prov')
# Step 7: Add tagged service offering
self.testdata['service_offerings']['tiny']['tags'] = 'disable_prov'
self.testdata["service_offerings"]["tiny"]["storagetype"] = 'local'
self.tagged_so = ServiceOffering.create(
self.userapiclient, self.testdata['service_offerings'])
self.testdata['service_offerings']['tiny']['tags'] = ' '
self.testdata["service_offerings"]["tiny"]["storagetype"] = ' '
self.cleanup.append(self.tagged_so)
# Step 8: Enable the pool
try:
self.debug("Step 8: Enabling pool")
self.list_storage = StoragePool.list(
self.userapiclient, id=storage_id)
if self.list_storage[0].state == 'Disabled':
StoragePool.update(
self.userapiclient,
id=storage_id,
enabled=True)
self.disabled_list.remove(storage_id)
except Exception as e:
raise e
# Step 9: Deploy VM using the tagged offering
self.debug("Step 9: Deploying VM using tagged offering")
self.virtual_machine_2 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.tagged_so.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_2.id, 'Running')
verify_vm_storage_pool(self, self.virtual_machine_2.id, storage_id)
# Step 10: Disable storage Pool
try:
self.list_storage = StoragePool.list(
self.userapiclient, id=storage_id)
if self.list_storage[0].state == 'Up':
StoragePool.update(
self.userapiclient,
id=storage_id,
enabled=False)
if storage_id not in self.disabled_list:
self.disabled_list.append(storage_id)
except Exception as e:
raise e
if value != 'host':
capacity_type = 2
else:
capacity_type = 9
# Step 11: View current capacity of storage pool
self.debug("Step 11: Getting current capacity...")
list_capacity_allocated = Capacities.list(
self.userapiclient, fetchlatest='true', type=capacity_type)
capacity_1 = list_capacity_allocated[0].capacityused
self.debug("Capacity 1: % s" % capacity_1)
# Step 12: Delete VM and check capacity is recalculated in disabled
# pool
self.debug("Step 12: Deleting Vm and re-calculating capacity")
self.virtual_machine_2.delete(self.userapiclient)
list_capacity_allocated = Capacities.list(
self.userapiclient, fetchlatest='true', type=capacity_type)
capacity_2 = list_capacity_allocated[0].capacityused
self.debug("Capacity 2: % s" % capacity_2)
self.assertGreater(
capacity_1,
capacity_2,
'Step 12: Capacity Used should be greater after VM delete although Storage is not enabled')
# Step 13: Deploy new VM with tagged offering again - should fail
with self.assertRaises(Exception):
self.virtual_machine_3 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.tagged_so.id,
zoneid=self.zone.id)
# Step 14: Capacity should not be altered in disabled pool since deploy
# VM failed
self.debug(
"Step 14: Checking capacity is not altered after deploy VM fails")
list_capacity_allocated = Capacities.list(
self.userapiclient, fetchlatest='true', type=capacity_type)
capacity_3 = list_capacity_allocated[0].capacityused
self.assertEqual(
capacity_2,
capacity_3,
"Step 14: Capacity Used shouldn't be altered since VM deployment failed")
class TestPathDisableStorage_Cross_Cluster(cloudstackTestCase):
"""
# Tests in this path requires to be run independently (not to be run in parallel with any other tests \
since it involves disabling/enabling storage pools and may cause unexpected failures in other tests
# This test at least 2 Clusters in the set up with suitable hosts for migration.
# For running the tests on local storage, ensure there are 2 local storage pools set up on each host
"""
@classmethod
def setUpClass(cls):
testClient = super(
TestPathDisableStorage_Cross_Cluster,
cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient)
cls.testdata['mode'] = cls.zone.networktype
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata['ostype'])
cls.testdata['template']['ostypeid'] = cls.template.ostypeid
if cls.template == FAILED:
cls.fail(
'get_template() failed to return template with description %s' %
cls.testdata['ostype'])
cls._cleanup = []
cls.disabled_list = []
cls.maint_list = []
cls.testdata['template_2']['zoneid'] = cls.zone.id
cls.testdata['template_2']['ostypeid'] = cls.template.ostypeid
cls.hypervisor = testClient.getHypervisorInfo()
try:
cls.account = Account.create(
cls.apiclient, cls.testdata['account'], admin=True)
cls.debug('Creating account')
cls._cleanup.append(cls.account)
cls.service_offering = ServiceOffering.create(
cls.apiclient, cls.testdata['service_offering'])
cls._cleanup.append(cls.service_offering)
cls.disk_offering = DiskOffering.create(
cls.apiclient, cls.testdata['disk_offering'])
cls.resized_disk_offering = DiskOffering.create(
cls.apiclient, cls.testdata['resized_disk_offering'])
cls._cleanup.append(cls.disk_offering)
cls.userapiclient = testClient.getUserApiClient(
UserName=cls.account.name, DomainName=cls.account.domain)
response = User.login(cls.userapiclient,
username=cls.account.name,
password=cls.testdata['account']['password'])
assert response.sessionkey is not None
except Exception as e:
cls.tearDownClass()
raise e
@classmethod
def tearDownClass(cls):
try:
cleanup_resources(cls.apiclient, cls._cleanup)
except Exception as e:
raise Exception('Warning:Exception during cleanup: %s' % e)
def setUp(self):
self.apiclient = self.testClient.getApiClient()
self.cleanup = []
def tearDown(self):
if self.disabled_list:
for poolid in self.disabled_list:
if StoragePool.list(self.userapiclient, id=poolid)[
0].state == 'Disabled':
try:
StoragePool.update(
self.userapiclient, id=poolid, enabled=True)
self.debug('Enabling: % s ' % poolid)
except Exception as e:
self.fail("Couldn't enable storage % s" % id)
try:
cleanup_resources(self.apiclient, self.cleanup)
except Exception as e:
self.fail('Warning: Exception during cleanup : %s' % e)
@attr(tags=['advanced', 'advancedsg', 'basic'], required_hardware='false')
def test_01_cross_cluster_attach_disk(self):
"""
Test Steps:
========
1. Deploy VM in one cluster
2. Migrate to other cluster
3. Add data disk, Attach to VM
4. Disable first storage pool
5. List for migration should not list the first pool anymore
6. Stop VM and detach disk
7. Enable first Pool
8. Migrate root to first pool
9. Now disable first pool again
10. Attach the disk which is running from enabled pool - Should fail
11.Enable pool again
12. Attach disk should now pass
"""
if self.hypervisor.lower() == 'lxc':
self.skipTest("Not running rest of tests in lxc")
cluster_id_list = []
clusters = list_clusters(self.userapiclient, listall='true')
if len(clusters) == 1:
raise unittest.SkipTest('Found only one cluster... skipping test')
for cluster in clusters:
try:
self.debug('Processing for cluster % s ' % cluster.id)
self.list_storage = StoragePool.list(
self.userapiclient, clusterid=cluster.id, scope='CLUSTER')
count_st_pools = len(self.list_storage)
if count_st_pools > 1:
self.debug(
'Found % s storage pools in cluster % s, keeping one and disabling rest' %
(count_st_pools, cluster.id))
for pool in self.list_storage[1:]:
self.disabled_pool_1 = self.list_storage[1]
if pool.state == 'Up':
self.debug(
'Trying to disable storage %s' %
pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
raise e
elif count_st_pools == 1:
self.debug('Only one cluster wide storage found')
else:
self.fail('No cluster wide storage pools found')
except Exception as e:
raise e
try:
self.list_storage = StoragePool.list(
self.userapiclient, scope='ZONE')
if self.list_storage:
for pool in self.list_storage:
if pool.state == 'Up':
self.debug('Trying to disable storage % s' % pool.id)
try:
StoragePool.update(
self.userapiclient, id=pool.id, enabled=False)
self.disabled_list.append(pool.id)
self.debug(
'Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
self.fail("Couldn't disable storage % s" % pool.id)
else:
self.debug('No zone wide storage pools found')
except Exception as e:
raise e
# Step 1: Deploy VM in a cluster
self.virtual_machine_1 = VirtualMachine.create(
self.userapiclient,
self.testdata['small'],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering.id,
zoneid=self.zone.id)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
root_vol = Volume.list(
self.userapiclient,
virtualmachineid=self.virtual_machine_1.id,
type='ROOT')[0]
storage_1 = root_vol.storageid
host_1 = self.virtual_machine_1.hostid
self.debug(
"Step 1: VM1 is running on % s host and % s storage pool" %
(host_1, storage_1))
# Step 2: Live Migrate VM to another cluster
hosts_for_migration = Host.listForMigration(
self.userapiclient, virtualmachineid=self.virtual_machine_1.id)
self.debug(
'Step 2: List of hosts suitable for migration: % s ' %
hosts_for_migration)
host_2 = None
for host in hosts_for_migration:
self.debug(
'Step 2: Host Requires storage motion is % s ' %
host.requiresStorageMotion)
if host.requiresStorageMotion:
host_2 = host.id
if host_2:
self.debug(
'Step 2: Migrating VM % s to Host % s' %
(self.virtual_machine_1.id, host_2))
self.virtual_machine_1.migrate_vm_with_volume(
self.userapiclient, hostid=host_2)
else:
self.fail('Step 2: No host found suitable for migration')
# Step 3: Add data disk and attach to VM
self.volume_1 = Volume.create(self.userapiclient,
services=self.testdata['volume'],
diskofferingid=self.disk_offering.id,
zoneid=self.zone.id)
self.virtual_machine_1.attach_volume(self.userapiclient, self.volume_1)
list_volume = Volume.list(self.userapiclient, id=self.volume_1.id)
self.assertEqual(
list_volume[0].virtualmachineid,
self.virtual_machine_1.id,
'Step 3: Check if volume state (attached) is reflected')
self.debug(
'Step 3: volume id:% s successfully attached to vm id % s' %
(self.volume_1.id, self.virtual_machine_1.id))
root_vol = Volume.list(
self.userapiclient,
virtualmachineid=self.virtual_machine_1.id,
type='ROOT')[0]
storage_2 = root_vol.storageid
data_vol = Volume.list(
self.userapiclient,
virtualmachineid=self.virtual_machine_1.id,
type='DATA')[0]
self.debug(
"Step 3: Data Volume is in storage pool: % s" %
data_vol.storageid)
self.assertEqual(
data_vol.storageid,
root_vol.storageid,
"Step 3: Root and Data disk should be running from 2nd storage pool where the VM was live migrated")
# Step 4: Disable first Storage Pool and verify it is not listed in
# hosts suitable for migration
try:
StoragePool.update(self.userapiclient, id=storage_1, enabled=False)
self.disabled_list.append(storage_1)
self.debug(
'Step 4: Appended to list of disabled pools. List is now: % s ' %
self.disabled_list)
except Exception as e:
self.fail("Step 4: Couldn't disable storage % s" % storage_1)
# Step 5: Disabled pool shouldn't be listed in hostsforMigration since
# all pools in the cluster are disabled
hosts_for_migration = Host.listForMigration(
self.userapiclient, virtualmachineid=self.virtual_machine_1.id)
self.debug(
"Step 5: List of Hosts For Migration is % s" %
hosts_for_migration)
if hosts_for_migration:
for host in hosts_for_migration:
if host_1 == host.id:
self.fail(
"Step 5: All pools in the cluster are disabled, hence host should not be listed for migration")
# Step 6: Stop VM and Detach Disk
self.virtual_machine_1.stop(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Stopped')
verify_vm_storage_pool(self, self.virtual_machine_1.id, storage_2)
self.debug("Step 6: Stopping VM and detaching disk")
self.virtual_machine_1.detach_volume(
self.userapiclient, volume=self.volume_1)
# Step 7, 8: Enable Pool for Migrating VM and disable again
try:
StoragePool.update(self.userapiclient, id=storage_1, enabled=True)
if storage_1 in self.disabled_list:
self.disabled_list.remove(storage_1)
except Exception as e:
self.fail("Step 7: Couldn't enable storage % s" % storage_1)
self.virtual_machine_1.start(self.userapiclient)
verify_vm_state(self, self.virtual_machine_1.id, 'Running')
try:
self.debug(
'Step 8: Migrating VM % s to Host % s' %
(self.virtual_machine_1.id, host_1))
self.virtual_machine_1.migrate_vm_with_volume(
self.userapiclient, hostid=host_1)
except Exception as e:
self.fail(
"Step 8: Couldn't live migrate VM to host % s due to % s" %
(host_1, e))
# Step 9: disable pool again
try:
StoragePool.update(self.userapiclient, id=storage_1, enabled=False)
self.debug("Step 9: Disabling storage pool: % s " % storage_1)
self.disabled_list.append(storage_1)
except Exception as e:
self.fail("Step 9: Couldn't disable storage % s" % storage_1)
st_list = StoragePool.list(self.userapiclient, id=storage_1)
self.debug(
"9.5 Status of storage pool 1 % s is % s " %
(st_list[0].name, st_list[0].state))
# Step 10: Try to attach data disk running from enabled pool with Root
# running in disabled pool - this should fail
with self.assertRaises(Exception):
self.virtual_machine_1.attach_volume(
self.userapiclient, self.volume_1)
self.debug(
"Step 10: Trying to attach volume % s" %
self.volume_1.id)
# Step 11: Enable the pool and try to attach again - this should pass
try:
StoragePool.update(self.userapiclient, id=storage_1, enabled=True)
self.debug("Step 11: Enable storage pool: % s " % storage_1)
self.disabled_list.remove(storage_1)
except Exception as e:
self.fail("Step 11: Couldn't enable storage % s" % storage_1)
# Step 12: Repeat attach volume - should succeed
self.virtual_machine_1.attach_volume(self.userapiclient, self.volume_1)
self.debug("Step 12: Trying to attach volume")
list_volume = Volume.list(self.userapiclient, id=self.volume_1.id)
self.assertEqual(
list_volume[0].virtualmachineid,
self.virtual_machine_1.id,
'Step 12: Check if volume state (attached) is reflected')
self.debug(
'Step 12: volume id:%s successfully attached to vm id%s' %
(self.volume_1.id, self.virtual_machine_1.id))