blob: 5b821bcb5dafdebaf2ee7ddb93bffb918d77acf1 [file] [log] [blame]
# 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.
""" Test cases for Test Paths Storage Migration
"""
from nose.plugins.attrib import attr
from marvin.cloudstackTestCase import cloudstackTestCase
import unittest
from marvin.lib.utils import (cleanup_resources)
from marvin.lib.base import (Account,
ServiceOffering,
DiskOffering,
Volume,
Template,
VirtualMachine,
StoragePool,
Snapshot
)
from marvin.lib.common import (get_domain,
get_zone,
get_template,
list_volumes,
list_virtual_machines,
createChecksum,
compareChecksum,
list_storage_pools,
list_clusters,
list_hosts,
validateList
)
from marvin.codes import (PASS,
ZONETAG1,
CLUSTERTAG1)
from marvin.cloudstackAPI import (deleteVolume)
from marvin.sshClient import SshClient
import time
from threading import Thread
def GetDestinationPool(self,
poolsToavoid,
migrateto
):
""" Get destination pool which has scope same as migrateto
and which is not in avoid set
"""
destinationPool = None
# Get Storage Pool Id to migrate to
for storagePool in self.pools:
if storagePool.scope == migrateto:
if storagePool.name not in poolsToavoid:
destinationPool = storagePool
break
return destinationPool
def MigrateRootVolume(self,
vm,
destinationPool,
expectexception=False):
""" Migrate given volume to type of storage pool mentioned in migrateto:
Inputs:
1. volume: Volume to be migrated
2. migrate_to: Scope of desired Storage pool to which volume
is to be migrated
3. expectexception: If exception is expected while migration
"""
if expectexception:
with self.assertRaises(Exception):
VirtualMachine.migrate(
vm,
self.apiclient,
# virtualmachineid=vm.id,
storageid=destinationPool.id,
)
else:
VirtualMachine.migrate(
vm,
self.apiclient,
# virtualmachineid=vm.id,
storageid=destinationPool.id,
)
migrated_vm_response = list_virtual_machines(
self.apiclient,
id=vm.id
)
self.assertEqual(
isinstance(migrated_vm_response, list),
True,
"Check list virtual machines response for valid list"
)
self.assertNotEqual(
migrated_vm_response,
None,
"Check if virtual machine exists in ListVirtualMachines"
)
migrated_vm = migrated_vm_response[0]
root_volumes_cluster_list = Volume.list(
self.apiclient,
virtualmachineid=migrated_vm.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
self.assertEqual(
root_volume_cluster.storage,
destinationPool.name,
"Check volume is on migrated pool"
)
return
def MigrateDataVolume(self,
volume,
destinationPool,
islive=False,
expectexception=False
):
""" Migrate given volume to type of storage pool mentioned in migrateto:
Inputs:
1. volume: Volume to be migrated
2. migrate_to: Scope of desired Storage pool to which volume
is to be migrated
3. expectexception: If exception is expected while migration
"""
if expectexception:
with self.assertRaises(Exception):
Volume.migrate(
self.apiclient,
volumeid=volume.id,
storageid=destinationPool.id,
livemigrate=islive
)
else:
Volume.migrate(
self.apiclient,
volumeid=volume.id,
storageid=destinationPool.id,
livemigrate=islive
)
migrated_volume_response = list_volumes(
self.apiclient,
id=volume.id
)
self.assertEqual(
isinstance(migrated_volume_response, list),
True,
"Check list volumes response for valid list"
)
self.assertNotEqual(
migrated_volume_response,
None,
"Check if volume exists in ListVolumes"
)
migrated_volume = migrated_volume_response[0]
self.assertEqual(
str(migrated_volume.state).lower(),
'ready',
"Check migrated volume is in Ready state"
)
self.assertEqual(
migrated_volume.storage,
destinationPool.name,
"Check volume is on migrated pool"
)
return
class TestStorageMigration(cloudstackTestCase):
@classmethod
def setUpClass(cls):
testClient = super(TestStorageMigration, cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.hypervisor = cls.testClient.getHypervisorInfo()
# Get Zone, Domain and templates
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient, testClient.getZoneForTests())
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata["ostype"])
cls._cleanup = []
if cls.hypervisor.lower() not in [
"vmware",
"kvm",
"xenserver",
"hyper-v"]:
raise unittest.SkipTest(
"Storage migration not supported on %s" %
cls.hypervisor)
try:
cls.pools = StoragePool.list(cls.apiclient, zoneid=cls.zone.id)
except Exception as e:
raise unittest.SkipTest(e)
try:
# Create an account
cls.account = Account.create(
cls.apiclient,
cls.testdata["account"],
domainid=cls.domain.id
)
cls._cleanup.append(cls.account)
# Create user api client of the account
cls.userapiclient = testClient.getUserApiClient(
UserName=cls.account.name,
DomainName=cls.account.domain
)
# Create Service offering
cls.service_offering = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"]
)
cls._cleanup.append(cls.service_offering)
cls.service_offering_zone1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"],
tags=ZONETAG1
)
cls._cleanup.append(cls.service_offering_zone1)
cls.service_offering_cluster1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"],
tags=CLUSTERTAG1
)
cls._cleanup.append(cls.service_offering_cluster1)
# If local storage is enabled, alter the offerings to use
# localstorage
if cls.zone.localstorageenabled:
cls.testdata["service_offering"]["storagetype"] = 'local'
cls.service_offering_local1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"]
)
cls._cleanup.append(cls.service_offering_local1)
# Create Disk offering
cls.disk_offering_zone1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"],
tags=ZONETAG1
)
cls._cleanup.append(cls.disk_offering_zone1)
cls.disk_offering_cluster1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"],
tags=CLUSTERTAG1
)
cls._cleanup.append(cls.disk_offering_cluster1)
cls.new_virtual_machine = VirtualMachine.create(
cls.apiclient,
cls.testdata["small"],
templateid=cls.template.id,
accountid=cls.account.name,
domainid=cls.account.domainid,
serviceofferingid=cls.service_offering.id,
zoneid=cls.zone.id,
mode=cls.zone.networktype
)
# If local storage is enabled, alter the offerings to use
# localstorage
if cls.zone.localstorageenabled:
cls.testdata["disk_offering"]["storagetype"] = 'local'
cls.disk_offering_local1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"]
)
cls._cleanup.append(cls.disk_offering_local1)
except Exception as e:
cls.tearDownClass()
raise e
return
@classmethod
def tearDownClass(cls):
try:
cleanup_resources(cls.apiclient, reversed(cls._cleanup))
except Exception as e:
raise Exception("Warning: Exception during cleanup : %s" % e)
def setUp(self):
self.apiclient = self.testClient.getApiClient()
self.dbclient = self.testClient.getDbConnection()
self.cleanup = []
def tearDown(self):
for storagePool in self.pools:
StoragePool.update(self.apiclient, id=storagePool.id, tags="")
super(TestStorageMigration,self).tearDown()
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_01_migrate_root_and_data_disk_nonlive(self):
""" Test migrate Volume (root and data disk)
# 1. Deploy a VM on cluster wide primary storage.
# 2. Migrate root and data volume from cluster-to-cluster,
# cluster-to-zone, cluster-to-local.
# 3. Deploy a VM on zone wide primary storage..
# 4. Migrate root and data volume from zone-to-zone, zone-to-local.
# 5. Deploy a VM on local storage.
# 6. Migrate root and data volume from local-to-local.
Each Migration has following steps:
a. Write data to disk, create checksum
b. Migrate the volume to suitable pool
c. Attach disk to VM and compare checksum with
checksum of data on disk, they should match
In addition to this,
Create snapshot of root and data disk after migration.
For root disk, create template from snapshot,
deploy Vm and compare checksum
For data disk, Create volume from snapshot,
attach to VM and compare checksum
"""
# Skipping test case for XenSever because ZWPS scenarios present in the test case
# Skipping for Vmware because on Vmware zwps and cwps can not exist at the same time
# so the test case for Vmware is written separately
if self.hypervisor.lower() in ["xenserver", "vmware"]:
self.skipTest("Skip test case for %s" % self.hypervisor.lower())
try:
self.pools = StoragePool.list(self.apiclient, zoneid=self.zone.id)
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "ZONE")) >= 2,\
"There must be at least two zone wide\
storage pools available in the setup"
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "CLUSTER")) >= 2,\
"There must be at least two cluster wide\
storage pools available in the setup"
except Exception as e:
self.skipTest(e)
# Adding tags to Storage Pools
cluster_no = 1
zone_no = 1
self.debug("Storage Pools: %s" % self.pools)
for storagePool in self.pools:
if storagePool.scope == "ZONE":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['zwps' + repr(zone_no)])
zone_no += 1
elif storagePool.scope == "CLUSTER":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['cwps' + repr(cluster_no)])
cluster_no += 1
# Step 1
# Create VM on CWPS
vm_cluster = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume
root_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
# Create DATA Volume on Cluster Wide Storage
data_volume_clust = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust
)
data_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust.id
)
root_vol_snap = Snapshot.create(
self.apiclient,
root_volume_cluster.id)
data_vol_snap = Snapshot.create(
self.apiclient,
data_volume_clust.id)
vm_cluster.detach_volume(
self.apiclient,
data_volume_clust)
# Step 2
# Migrate ROOT Volume from CWPS to other CWPS, this consists of below 3 steps
# 1. Create Checksum
# 2. Migrate Volume
# 3. Compare checksum with data on volume on new pool
checksum_random_root_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=root_volume_cluster,
disk_type="rootdiskdevice")
vm_cluster.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"CLUSTER")
MigrateRootVolume(self, vm_cluster, destinationPool)
vm_cluster.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_cluster,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
self.debug("Done with compare checksum")
vm_cluster.stop(self.userapiclient)
# Try to Migrate ROOT Volume from CWPS to ZWPS
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"ZONE")
MigrateRootVolume(
self,
vm_cluster,
destinationPool)
vm_cluster.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_cluster,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
vm_cluster.stop(self.userapiclient)
# Try to Migrate ROOT Volume from CWPS to Local
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"HOST")
MigrateRootVolume(
self,
vm_cluster,
destinationPool,
expectexception=True)
vm_cluster.start(self.userapiclient)
checksum_random_data_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_volumes_cluster_list[0],
disk_type="datadiskdevice_1")
vm_cluster.detach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
vm_cluster.stop(self.userapiclient)
# Migrate DATA Volume from CWPS to other CWPS - Create checksum,
# migrate volume, compare checksum
destinationPool = GetDestinationPool(
self,
[data_volumes_cluster_list[0].storage],
"CLUSTER")
MigrateDataVolume(
self,
data_volumes_cluster_list[0],
destinationPool)
vm_cluster.start(self.userapiclient)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_cluster_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Add more data to disks
data_volume_clust_2 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust_2.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust_2
)
data_disk_2_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust_2.id
)
# Ensure we can add data to newly added disks
createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_disk_2_volumes_cluster_list[0],
disk_type="datadiskdevice_2")
vm_cluster.detach_volume(
self.apiclient,
data_volume_clust_2
)
templateFromSnapshot = Template.create_from_snapshot(
self.apiclient,
root_vol_snap,
self.testdata["template_2"])
vm_from_temp = VirtualMachine.create(
self.apiclient,
self.testdata["small"],
templateid=templateFromSnapshot.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
root_volumes_snap_list = Volume.list(
self.apiclient,
virtualmachineid=vm_from_temp.id,
type='ROOT',
listall=True
)
root_volume_snap = root_volumes_snap_list[0]
createChecksum(
service=self.testdata,
virtual_machine=vm_from_temp,
disk=root_volume_snap,
disk_type="rootdiskdevice")
templateFromSnapshot.delete(self.apiclient)
volumeFormSnap = Volume.create_from_snapshot(
self.apiclient,
data_vol_snap.id,
self.testdata["volume"],
account=self.account.name,
domainid=self.account.domainid,
zoneid=self.zone.id
)
vm_from_temp.attach_volume(
self.userapiclient,
volumeFormSnap
)
data_from_snap = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=volumeFormSnap.id
)
vm_from_temp.reboot(self.userapiclient)
createChecksum(
service=self.testdata,
virtual_machine=vm_from_temp,
disk=data_from_snap[0],
disk_type="datadiskdevice_1")
vm_from_temp.detach_volume(
self.userapiclient,
volumeFormSnap
)
volumeFormSnap.delete(self.apiclient)
vm_from_temp.delete(self.apiclient)
vm_cluster.stop(self.userapiclient)
# Try to Migrate DATA Volume from CWPS to ZWPS
destinationPool = GetDestinationPool(
self,
[data_volumes_cluster_list[0].storage],
"ZONE")
MigrateDataVolume(
self,
data_volumes_cluster_list[0],
destinationPool)
vm_cluster.start(self.userapiclient)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.delete(self.apiclient)
vm_cluster.stop(self.userapiclient)
# Try to Migrate DATA Volume from CWPS to Local Storage
destinationPool = GetDestinationPool(
self,
[data_volumes_cluster_list[0].storage],
"HOST")
MigrateDataVolume(
self,
data_volumes_cluster_list[0],
destinationPool)
# Delete ROOT and DATA Volume from CWPS
self.debug("Deleting Volume %s" % data_volume_clust.id)
vm_cluster.detach_volume(self.apiclient, data_volume_clust)
# Delete volume:
data_volume_clust.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_clust.id,
), None, "Volume list should be empty")
# Destroy and expunge VM
vm_cluster.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_cluster.id
), None, "VM list should be empty")
# Step 3
# Create VM on ZWPS
vm_zone = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_zone1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume Id
root_volumes_zone_list = list_volumes(
self.apiclient,
virtualmachineid=vm_zone.id,
type='ROOT',
listall=True
)
root_volume_zone = root_volumes_zone_list[0]
# Create DATA Volume on ZWPS
data_volume_zone = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_zone1.id
)
self.debug("Created volume with ID: %s" % data_volume_zone.id)
data_volumes_zone_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_zone.id
)
vm_zone.attach_volume(
self.userapiclient,
data_volume_zone
)
# Step 4
# Migrate ROOT Volume from ZWPS to other ZWPS
checksum_random_root_zone = createChecksum(
service=self.testdata,
virtual_machine=vm_zone,
disk=data_volumes_zone_list[0],
disk_type="rootdiskdevice")
vm_zone.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self, [
root_volume_zone.storage], "ZONE")
MigrateRootVolume(self, vm_zone, destinationPool)
vm_zone.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_zone,
disk_type="rootdiskdevice",
virt_machine=vm_zone
)
vm_zone.stop(self.userapiclient)
# Try to Migrate ROOT Volume from ZWPS to Local Storage
destinationPool = GetDestinationPool(
self, [
root_volume_zone.storage], "HOST")
MigrateRootVolume(self, vm_zone, destinationPool, expectexception=True)
# Try to Migrate ROOT Volume from ZWPS to Cluster wide Storage
destinationPool = GetDestinationPool(
self, [
root_volume_zone.storage], "CLUSTER")
MigrateRootVolume(
self,
vm_zone,
destinationPool) # , expectexception=True)
vm_zone.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_zone,
disk_type="rootdiskdevice",
virt_machine=vm_zone
)
checksum_random_data_zone = createChecksum(
service=self.testdata,
virtual_machine=vm_zone,
disk=data_volumes_zone_list[0],
disk_type="datadiskdevice_1")
vm_zone.stop(self.userapiclient)
# Migrate DATA Volume from ZWPS to other ZWPS
destinationPool = GetDestinationPool(
self,
[data_volumes_zone_list[0].storage],
"ZONE")
MigrateDataVolume(self, data_volumes_zone_list[0], destinationPool)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_zone_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_zone,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_zone_list[0])
vm_zone.stop(self.userapiclient)
# Try to Migrate DATA Volume from ZWPS to Local Storage
destinationPool = GetDestinationPool(
self, [
data_volume_zone.storage], "HOST")
MigrateDataVolume(
self,
data_volume_zone,
destinationPool,
expectexception=True)
# Try to Migrate DATA Volume from ZWPS to Cluster wide Storage
destinationPool = GetDestinationPool(
self, [
data_volume_zone.storage], "CLUSTER")
MigrateDataVolume(
self,
data_volume_zone,
destinationPool)
vm_zone.start(self.userapiclient)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_zone_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_zone,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_zone_list[0])
# Delete ROOT and DATA Volume from ZWPS
self.debug("Deleting Volume %s" % data_volume_zone.id)
vm_zone.detach_volume(self.apiclient, data_volume_zone)
# Delete volume
data_volume_zone.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_zone.id,
), None, "Volume list should be empty")
# Destroy and expunge VM
vm_zone.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_zone.id
), None, "VM list should be empty")
# Step 5
localStoragePoolsPresent = True
try:
self.assertEqual(
len(list(storagePool for storagePool in self.pools
if storagePool.scope == "HOST")), 2)
except Exception as e:
localStoragePoolsPresent = False
if localStoragePoolsPresent:
# Create VM on local storage
vm_local = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_local1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume id
root_volumes_local_list = list_volumes(
self.apiclient,
virtualmachineid=vm_local.id,
type='ROOT',
listall=True
)
root_volume_local = root_volumes_local_list[0]
# Create DATA Volume on local storage
data_volume_local = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_local1.id
)
self.debug("Created volume with ID: %s" % data_volume_local.id)
data_volumes_local_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_local.id
)
vm_local.attach_volume(
self.userapiclient,
data_volume_local
)
# Step 6
# Migrate root and data volume from Local to another Local storage
checksum_random_root_local = createChecksum(
service=self.testdata,
virtual_machine=vm_local,
disk=data_volumes_local_list[0],
disk_type="rootdiskdevice")
vm_local.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self, [
root_volume_local.storage], "HOST")
MigrateRootVolume(self, vm_local, destinationPool)
vm_local.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_local,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
checksum_random_data_local = createChecksum(
service=self.testdata,
virtual_machine=vm_local,
disk=data_volumes_local_list[0],
disk_type="datadiskdevice_1")
vm_local.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self,
[data_volumes_local_list[0].storage],
"HOST")
MigrateDataVolume(
self,
data_volumes_local_list[0],
destinationPool)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_local_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
vm_local.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_local,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_local_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Delete ROOT and DATA Volume from Local Storage
self.debug("Deleting Volume %s" % data_volume_local.id)
vm_local.detach_volume(self.apiclient, data_volume_local)
# Delete volume
data_volume_local.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_local.id,
), None, "Volumes list should be empty")
# Destroy and expunge VM
vm_local.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_local.id
), None, "VM list should be empty")
return
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_02_migration_nonlive_xenserver_supported(self):
""" Test migrate Volume (root and data disk) for Hypervisor Xenserver
# 1. Deploy a VM on cluster wide primary storage.
# 2. Migrate root and data volume from
cluster-to-cluster,cluster-to-local.
# 3. Deploy a VM on local storage.
# 4. Migrate root and data volume from local-to-local.
Each Migration has following steps:
a. Write data to disk, create checksum
b. Migrate the volume to suitable pool
c. Attach disk to VM and compare checksum with
checksum of data on disk, they should match
In addition to this,
Create snapshot of root and data disk after migration.
For root disk, create template from snapshot, deploy Vm and compare checksum
For data disk, Create volume from snapshot, attach to VM and compare checksum
"""
# Check if Hypervisor is Xenserver
if self.hypervisor.lower() != "xenserver":
self.skipTest("This test case is written specifically for xenserver,\
it does not include ZWPS scenarios")
try:
self.pools = StoragePool.list(self.apiclient, zoneid=self.zone.id)
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "CLUSTER")) >= 2,\
"There must be at least two cluster wide\
storage pools available in the setup"
except Exception as e:
self.skipTest(e)
# Adding tags to Storage Pools
cluster_no = 1
self.debug("Storage Pools: %s" % self.pools)
for storagePool in self.pools:
if storagePool.scope == "CLUSTER":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['cwps' + repr(cluster_no)])
cluster_no += 1
# Create VM on CWPS
vm_cluster = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume Id
root_volumes_cluster_list = Volume.list(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
data_volume_clust = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust
)
data_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust.id
)
root_vol_snap = Snapshot.create(
self.apiclient,
root_volume_cluster.id)
data_vol_snap = Snapshot.create(
self.apiclient,
data_volume_clust.id)
vm_cluster.detach_volume(
self.apiclient,
data_volume_clust)
# Migrate ROOT Volume from CWPS to other CWPS
checksum_random_root_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=root_volume_cluster,
disk_type="rootdiskdevice")
vm_cluster.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"CLUSTER")
MigrateRootVolume(self, vm_cluster, destinationPool)
vm_cluster.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_cluster,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
self.debug("Done with compare checksum after first checksum")
vm_cluster.start(self.userapiclient)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust
)
vm_cluster.reboot(self.userapiclient)
checksum_random_data_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_volumes_cluster_list[0],
disk_type="datadiskdevice_1")
vm_cluster.stop(self.userapiclient)
# Migrate DATA Volume from CWPS to other CWPS
destinationPool = GetDestinationPool(
self,
[data_volumes_cluster_list[0].storage],
"CLUSTER")
MigrateDataVolume(self, data_volumes_cluster_list[0], destinationPool)
vm_cluster.start(self.userapiclient)
vm_cluster.detach_volume(self.apiclient, data_volumes_cluster_list[0])
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_cluster_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# snapshot test case t14 compare checksum for same VM
vm_cluster.attach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
vm_cluster.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=vm_cluster
)
# Add more data to disks
data_volume_clust_2 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust_2.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust_2
)
data_disk_2_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust_2.id
)
createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_disk_2_volumes_cluster_list[0],
disk_type="datadiskdevice_2")
vm_cluster.detach_volume(
self.apiclient,
data_volume_clust_2
)
vm_cluster.stop(self.userapiclient)
# Try to Migrate ROOT Volume from CWPS to Local
destinationPool = GetDestinationPool(
self, [
root_volume_cluster.storage], "HOST")
MigrateRootVolume(
self,
vm_cluster,
destinationPool,
expectexception=True)
# Try to Migrate DATA Volume from CWPS to Local Storage
destinationPool = GetDestinationPool(
self,
[data_volumes_cluster_list[0].storage],
"HOST")
MigrateDataVolume(
self,
data_volumes_cluster_list[0],
destinationPool,
expectexception=True)
# Restore snapshot to preveous stage
# Convert root snap to template and boot vm from that n then check data
# Convert data snap to volume and attach it toa VM and then check data
templateFromSnapshot = Template.create_from_snapshot(
self.apiclient,
root_vol_snap,
self.testdata["template_2"])
vm_from_temp = VirtualMachine.create(
self.apiclient,
self.testdata["small"],
templateid=templateFromSnapshot.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
root_volumes_snap_list = Volume.list(
self.apiclient,
virtualmachineid=vm_from_temp.id,
type='ROOT',
listall=True
)
root_volume_snap = root_volumes_snap_list[0]
createChecksum(
service=self.testdata,
virtual_machine=vm_from_temp,
disk=root_volume_snap,
disk_type="rootdiskdevice")
templateFromSnapshot.delete(self.apiclient)
volumeFormSnap = Volume.create_from_snapshot(
self.apiclient,
data_vol_snap.id,
self.testdata["volume"],
account=self.account.name,
domainid=self.account.domainid,
zoneid=self.zone.id
)
vm_from_temp.attach_volume(
self.userapiclient,
volumeFormSnap
)
data_from_snap = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=volumeFormSnap.id
)
vm_from_temp.reboot(self.userapiclient)
createChecksum(
service=self.testdata,
virtual_machine=vm_from_temp,
disk=data_from_snap[0],
disk_type="datadiskdevice_1")
vm_from_temp.detach_volume(
self.userapiclient,
volumeFormSnap
)
volumeFormSnap.delete(self.apiclient)
vm_from_temp.delete(self.apiclient)
# Delete ROOT and DATA Volume from CWPS
self.debug("Deleting Volume %s" % data_volume_clust.id)
vm_cluster.detach_volume(self.apiclient, data_volume_clust)
# Delete volume:
data_volume_clust.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_clust.id,
), None, "Volume list should be empty")
# Destroy and expunge VM
vm_cluster.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_cluster.id
), None, "VM list should be empty")
localStoragePoolsAvailable = True
try:
self.assertEqual(
len(list(storagePool for storagePool in self.pools
if storagePool.scope == "HOST")), 2)
except Exception as e:
localStoragePoolsAvailable = False
if localStoragePoolsAvailable:
# Create VM on local storage
vm_local = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_local1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume id
root_volumes_local_list = Volume.list(
self.apiclient,
virtualmachineid=vm_local.id,
type='ROOT',
listall=True
)
root_volume_local = root_volumes_local_list[0]
# Create DATA Volume on local storage
data_volume_local = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_local1.id
)
self.debug("Created volume with ID: %s" % data_volume_local.id)
data_volumes_local_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_local.id
)
vm_local.attach_volume(
self.userapiclient,
data_volume_local
)
vm_local.reboot(self.userapiclient)
createChecksum(
service=self.testdata,
virtual_machine=vm_local,
disk=root_volume_local,
disk_type="rootdiskdevice")
vm_local.stop(self.userapiclient)
# Migrate root and data volume from Local to another Local storage
destinationPool = GetDestinationPool(
self, [
root_volume_local.storage], "HOST")
MigrateRootVolume(
self,
vm_local,
destinationPool,
expectexception=True)
vm_local.detach_volume(self.apiclient, data_volume_local)
destinationPool = GetDestinationPool(
self,
[data_volumes_local_list[0].storage],
"HOST")
MigrateDataVolume(
self,
data_volumes_local_list[0],
destinationPool,
expectexception=True)
# Delete ROOT and DATA Volume from Local Storage
self.debug("Deleting Volume %s" % data_volume_local.id)
# Delete volume
data_volume_local.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_local.id,
), None, "Volumes list should be empty")
# Destroy and expunge VM
vm_local.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_local.id
), None, "VM list should be empty")
return
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_03_migrate_root_and_data_disk_nonlive_cwps_vmware(self):
""" Test migrate Volume (root and data disk)
# 1. Deploy a VM on cluster wide primary storage.
# 2. Migrate root and data volume from cluster-to-cluster
# 3. Deploy a VM on local storage.
# 4. Migrate root and data volume from local-to-local.
Each Migration has following steps:
a. Write data to disk, create checksum
b. Migrate the volume to suitable pool
c. Attach disk to VM and compare checksum with
checksum of data on disk, they should match
In addition to this,
Create snapshot of root and data disk after migration.
For root disk, create template from snapshot, deploy Vm and compare checksum
For data disk, Create volume from snapshot, attach to VM and compare checksum
"""
# Test case only written for Vmware hypervisor as it
# does not run CWPS and ZWPS scenatios together
if self.hypervisor.lower() is not "vmware":
self.skipTest("Skip test case for %s" % self.hypervisor.lower())
try:
self.pools = StoragePool.list(self.apiclient, zoneid=self.zone.id)
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "CLUSTER")) >= 2,\
"There must be at least two cluster wide\
storage pools available in the setup"
except Exception as e:
self.skipTest(e)
# Adding tags to Storage Pools
cluster_no = 1
self.debug("Storage Pools: %s" % self.pools)
for storagePool in self.pools:
if storagePool.scope == "CLUSTER":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['cwps' + repr(cluster_no)])
cluster_no += 1
# Step 1
# Create VM on CWPS
vm_cluster = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume Id
root_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
# Create DATA Volume on Cluster Wide Storage
data_volume_clust = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust
)
data_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust.id
)
root_vol_snap = Snapshot.create(
self.apiclient,
root_volume_cluster.id)
data_vol_snap = Snapshot.create(
self.apiclient,
data_volume_clust.id)
vm_cluster.detach_volume(
self.apiclient,
data_volume_clust)
# Step 2
# Migrate ROOT Volume from CWPS to other CWPS
checksum_random_root_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=root_volume_cluster,
disk_type="rootdiskdevice")
vm_cluster.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"CLUSTER")
MigrateRootVolume(self, vm_cluster, destinationPool)
vm_cluster.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_cluster,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
self.debug("Done with compare checksum")
vm_cluster.start(self.userapiclient)
checksum_random_data_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_volumes_cluster_list[0],
disk_type="datadiskdevice_1")
vm_cluster.detach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
vm_cluster.stop(self.userapiclient)
# Migrate DATA Volume from CWPS to other CWPS
destinationPool = GetDestinationPool(
self,
[data_volumes_cluster_list[0].storage],
"CLUSTER")
MigrateDataVolume(
self,
data_volumes_cluster_list[0],
destinationPool)
vm_cluster.start(self.userapiclient)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_cluster_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# snapshot test case t14 compare checksum for same VM
vm_cluster.attach_volume(
self.apiclient,
data_volumes_cluster_list[0]
)
vm_cluster.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=vm_cluster
)
# Add more data to disks
data_volume_clust_2 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust_2.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust_2
)
data_disk_2_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust_2.id
)
createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_disk_2_volumes_cluster_list[0],
disk_type="datadiskdevice_2")
vm_cluster.detach_volume(
self.apiclient,
data_volume_clust_2
)
templateFromSnapshot = Template.create_from_snapshot(
self.apiclient,
root_vol_snap,
self.testdata["template_2"])
vm_from_temp = VirtualMachine.create(
self.apiclient,
self.testdata["small"],
templateid=templateFromSnapshot.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
root_volumes_snap_list = Volume.list(
self.apiclient,
virtualmachineid=vm_from_temp.id,
type='ROOT',
listall=True
)
root_volume_snap = root_volumes_snap_list[0]
createChecksum(
service=self.testdata,
virtual_machine=vm_from_temp,
disk=root_volume_snap,
disk_type="rootdiskdevice")
templateFromSnapshot.delete(self.apiclient)
volumeFormSnap = Volume.create_from_snapshot(
self.apiclient,
data_vol_snap.id,
self.testdata["volume"],
account=self.account.name,
domainid=self.account.domainid,
zoneid=self.zone.id
)
vm_from_temp.attach_volume(
self.userapiclient,
volumeFormSnap
)
data_from_snap = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=volumeFormSnap.id
)
vm_from_temp.reboot(self.userapiclient)
createChecksum(
service=self.testdata,
virtual_machine=vm_from_temp,
disk=data_from_snap[0],
disk_type="datadiskdevice_1")
vm_from_temp.detach_volume(
self.userapiclient,
volumeFormSnap
)
volumeFormSnap.delete(self.apiclient)
vm_from_temp.delete(self.apiclient)
# Delete ROOT and DATA Volume from CWPS
self.debug("Deleting Volume %s" % data_volume_clust.id)
vm_cluster.detach_volume(self.apiclient, data_volume_clust)
# Delete volume:
data_volume_clust.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_clust.id,
), None, "Volume list should be empty")
# Destroy and expunge VM
vm_cluster.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_cluster.id
), None, "VM list should be empty")
localStoragePoolsPresent = True
# Step 5
try:
self.assertEqual(
len(list(storagePool for storagePool in self.pools
if storagePool.scope == "HOST")), 2)
except Exception as e:
localStoragePoolsPresent = False
if localStoragePoolsPresent:
# Create VM on local storage
vm_local = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_local1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume id
root_volumes_local_list = list_volumes(
self.apiclient,
virtualmachineid=vm_local.id,
type='ROOT',
listall=True
)
root_volume_local = root_volumes_local_list[0]
# Create DATA Volume on local storage
data_volume_local = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_local1.id
)
self.debug("Created volume with ID: %s" % data_volume_local.id)
data_volumes_local_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_local.id
)
vm_local.attach_volume(
self.userapiclient,
data_volume_local
)
# Step 6
# Migrate root and data volume from Local to another Local storage
checksum_random_root_local = createChecksum(
service=self.testdata,
virtual_machine=vm_local,
disk=data_volumes_local_list[0],
disk_type="rootdiskdevice")
vm_local.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self, [
root_volume_local.storage], "HOST")
MigrateRootVolume(self, vm_local, destinationPool)
vm_local.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_local,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
checksum_random_data_local = createChecksum(
service=self.testdata,
virtual_machine=vm_local,
disk=data_volumes_local_list[0],
disk_type="datadiskdevice_1")
vm_local.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self,
[data_volumes_local_list[0].storage],
"HOST")
MigrateDataVolume(
self,
data_volumes_local_list[0],
destinationPool)
vm_local.start(self.userapiclient)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_local_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_local,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_local_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Delete ROOT and DATA Volume from Local Storage
self.debug("Deleting Volume %s" % data_volume_local.id)
vm_local.detach_volume(self.apiclient, data_volume_local)
# Delete volume
data_volume_local.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_local.id,
), None, "Volumes list should be empty")
# Destroy and expunge VM
vm_local.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_local.id
), None, "VM list should be empty")
return
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_04_migrate_root_and_data_disk_nonlive_zwps_vmware(self):
""" Test migrate Volume (root and data disk)
# 1. Deploy a VM on zone wide primary storage..
# 2. Migrate root and data volume from zone-to-zone, zone-to-local.
Each Migration has following steps:
a. Write data to disk, create checksum
b. Migrate the volume to suitable pool
c. Attach disk to VM and compare checksum with
checksum of data on disk, they should match
"""
# Test case only written for Vmware hypervisor as it
# does not run CWPS and ZWPS scenatios together
if self.hypervisor.lower() is not "vmware":
self.skipTest("Skip test case for %s" % self.hypervisor.lower())
try:
self.pools = StoragePool.list(self.apiclient, zoneid=self.zone.id)
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "ZONE")) >= 2,\
"There must be at least two zone wide\
storage pools available in the setup"
except Exception as e:
self.skipTest(e)
# Adding tags to Storage Pools
zone_no = 1
self.debug("Storage Pools: %s" % self.pools)
for storagePool in self.pools:
if storagePool.scope == "ZONE":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['zwps' + repr(zone_no)])
zone_no += 1
# Step 3
# Create VM on ZWPS
vm_zone = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_zone1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume Id
root_volumes_zone_list = list_volumes(
self.apiclient,
virtualmachineid=vm_zone.id,
type='ROOT',
listall=True
)
root_volume_zone = root_volumes_zone_list[0]
# Create DATA Volume on ZWPS
data_volume_zone = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_zone1.id
)
self.debug("Created volume with ID: %s" % data_volume_zone.id)
data_volumes_zone_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_zone.id
)
vm_zone.attach_volume(
self.userapiclient,
data_volume_zone
)
# Step 4
# Migrate ROOT Volume from ZWPS to other ZWPS
checksum_random_root_zone = createChecksum(
service=self.testdata,
virtual_machine=vm_zone,
disk=data_volumes_zone_list[0],
disk_type="rootdiskdevice")
vm_zone.stop(self.userapiclient)
destinationPool = GetDestinationPool(
self, [
root_volume_zone.storage], "ZONE")
MigrateRootVolume(self, vm_zone, destinationPool)
vm_zone.start(self.userapiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_zone,
disk_type="rootdiskdevice",
virt_machine=vm_zone
)
checksum_random_data_zone = createChecksum(
service=self.testdata,
virtual_machine=vm_zone,
disk=data_volumes_zone_list[0],
disk_type="datadiskdevice_1")
vm_zone.stop(self.userapiclient)
# Migrate DATA Volume from ZWPS to other ZWPS
destinationPool = GetDestinationPool(
self,
[data_volumes_zone_list[0].storage],
"ZONE")
MigrateDataVolume(self, data_volumes_zone_list[0], destinationPool)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_zone_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_zone,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_zone_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Delete ROOT and DATA Volume from ZWPS
self.debug("Deleting Volume %s" % data_volume_zone.id)
vm_zone.detach_volume(self.apiclient, data_volume_zone)
# Delete volume
data_volume_zone.delete(self.apiclient)
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_zone.id,
), None, "Volume list should be empty")
# Destroy and expunge VM
vm_zone.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_zone.id
), None, "VM list should be empty")
return
class NegativeTestStorageMigration(cloudstackTestCase):
exceptionList = []
@classmethod
def setUpClass(cls):
testClient = super(
NegativeTestStorageMigration,
cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.hypervisor = cls.testClient.getHypervisorInfo()
# Get Zone, Domain and templates
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient, testClient.getZoneForTests())
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata["ostype"])
cls._cleanup = []
if cls.hypervisor.lower() not in [
"vmware",
"kvm",
"xenserver",
"hyper-v"]:
raise unittest.SkipTest(
"Storage migration not supported on %s" %
cls.hypervisor)
try:
cls.pools = StoragePool.list(cls.apiclient, zoneid=cls.zone.id)
assert len(list(storagePool for storagePool in cls.pools
if storagePool.scope == "ZONE")) >= 2,\
"There must be at least two zone wide\
storage pools available in the setup"
assert len(list(storagePool for storagePool in cls.pools
if storagePool.scope == "CLUSTER")) >= 2,\
"There must be at least two cluster wide\
storage pools available in the setup"
except Exception as e:
raise unittest.SkipTest(e)
try:
# Create an account
cls.account = Account.create(
cls.apiclient,
cls.testdata["account"],
domainid=cls.domain.id
)
cls._cleanup.append(cls.account)
# Create user api client of the account
cls.userapiclient = testClient.getUserApiClient(
UserName=cls.account.name,
DomainName=cls.account.domain
)
# Create Service offering
cls.service_offering_zone1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"],
tags=ZONETAG1
)
cls._cleanup.append(cls.service_offering_zone1)
cls.service_offering_cluster1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"],
tags=CLUSTERTAG1
)
cls._cleanup.append(cls.service_offering_cluster1)
# If local storage is enabled, alter the offerings to use
# localstorage
if cls.zone.localstorageenabled:
cls.testdata["service_offering"]["storagetype"] = 'local'
cls.service_offering_local1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"]
)
cls._cleanup.append(cls.service_offering_local1)
# Create Disk offering
cls.disk_offering_zone1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"],
tags=ZONETAG1
)
cls._cleanup.append(cls.disk_offering_zone1)
cls.disk_offering_cluster1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"],
tags=CLUSTERTAG1
)
cls._cleanup.append(cls.disk_offering_cluster1)
# If local storage is enabled, alter the offerings to use
# localstorage
if cls.zone.localstorageenabled:
cls.testdata["disk_offering"]["storagetype"] = 'local'
cls.disk_offering_local1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"]
)
cls._cleanup.append(cls.disk_offering_local1)
except Exception as e:
cls.tearDownClass()
raise e
return
@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.dbclient = self.testClient.getDbConnection()
self.cleanup = []
def tearDown(self):
try:
for storagePool in self.pools:
StoragePool.update(self.apiclient, id=storagePool.id, tags="")
cleanup_resources(self.apiclient, self.cleanup)
except Exception as e:
raise Exception("Warning: Exception during cleanup : %s" % e)
return
def createMigrationJob(self, volume):
try:
destinationPool = None
for storagePool in self.pools:
if storagePool.scope == "CLUSTER":
if storagePool.name != volume.storage:
destinationPool = storagePool
break
with self.assertRaises(Exception):
Volume.migrate(
self.apiclient,
volumeid=volume.id,
storageid=destinationPool.id,
livemigrate='false'
)
except Exception as e:
self.exceptionList.append(e)
def createTemplateJob(self, virtual_machine, root_volume):
try:
services = {"displaytext": "templ",
"name": "vol_template",
"ostypeid": virtual_machine.ostypeid}
with self.assertRaises(Exception):
Template.create(self.apiclient,
services,
volumeid=root_volume.id
)
except Exception as e:
self.exceptionList.append(e)
def createDestroyVmJob(self, virtual_machine):
try:
with self.assertRaises(Exception):
virtual_machine.delete(self.apiclient)
except Exception as e:
self.exceptionList.append(e)
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_01_migrate_data_disk_negative_test(self):
""" Negative test cases
# 1. Deploy a VM on cluster wide primary storage.
# 2. Add some data to disks and create checksum
# 3. Migrate root and data volume from cluster-to-cluster wide storage pool
# 4. While migration(ROOT disk) is in progress try following scenarios,
they should fail:
I. Take snapshot of the disk
II. Create Template from the volume
III. Destroy the instance
# 5. Compare checksum after migration
"""
# Adding tags to Storage Pools
cluster_no = 1
self.debug("Storage Pools: %s" % self.pools)
for storagePool in self.pools:
if storagePool.scope == "CLUSTER":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['cwps' + repr(cluster_no)])
cluster_no += 1
# Step 1
# Create VM on CWPS
vm_cluster = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
diskofferingid=self.disk_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume Id
disk_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='DATADISK',
listall=True
)
data_disk = disk_volumes_cluster_list[0]
root_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
# Step 2
# Calculate checksum of ROOT and DATA Disks
checksum_root_disk = self.createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=root_volume_cluster,
disk_type="rootdiskdevice")
checksum_data_disk = self.createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_disk,
disk_type="datadiskdevice_1")
volumes = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_disk.id
)
self.assertEqual(
isinstance(volumes, list),
True,
"Check list response returns a valid list"
)
volume = volumes[0]
vm_cluster.detach_volume(
self.apiclient,
volume
)
vm_cluster.stop(self.userapiclient)
try:
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"CLUSTER")
thread_1 = Thread(
target=MigrateRootVolume,
args=(
self,
vm_cluster,
destinationPool,
))
thread_2 = Thread(
target=self.createTemplateJob,
args=(
vm_cluster,
root_volume_cluster,
))
thread_1.start()
thread_2.start()
thread_1.join()
thread_2.join()
except:
self.debug("Error: unable to start thread")
try:
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"CLUSTER")
thread_3 = Thread(
target=MigrateRootVolume,
args=(
self,
vm_cluster,
destinationPool,
))
thread_4 = Thread(
target=self.createMigrationJob,
args=(
root_volume_cluster,
))
thread_3.start()
timeout = 60
while timeout >= 0:
if volume.state == "Migrating":
break
timeout -= 5
time.sleep(5)
thread_4.start()
thread_3.join()
thread_4.join()
except:
self.debug("Error: unable to start thread")
vm_cluster.start(self.userapiclient)
vm_cluster.attach_volume(
self.apiclient,
volume
)
vm_cluster.reboot(self.userapiclient)
disk_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='DATADISK',
listall=True
)
data_disk = disk_volumes_cluster_list[0]
root_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
self.debug("Done with create checksum")
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_root_disk,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_data_disk,
disk_type="datadiskdevice_1",
virt_machine=vm_cluster
)
vm_cluster.detach_volume(
self.userapiclient,
volume
)
cmd = deleteVolume.deleteVolumeCmd()
cmd.id = volume.id
self.apiclient.deleteVolume(cmd)
vm_cluster.stop(self.userapiclient)
try:
destinationPool = GetDestinationPool(
self,
[root_volume_cluster.storage],
"CLUSTER")
thread_5 = Thread(
target=MigrateRootVolume,
args=(
self,
vm_cluster,
destinationPool,
))
thread_6 = Thread(
target=self.createDestroyVmJob,
args=(
vm_cluster,
))
thread_5.start()
thread_6.start()
thread_5.join()
thread_6.join()
except:
self.debug("Error: unable to start thread")
# Raise exception if there was any exception raised from the threads
if self.exceptionList:
for i in self.exceptionList:
raise(i)
vm_cluster.delete(self.apiclient)
return
class TestLiveStorageMigration(cloudstackTestCase):
@classmethod
def setUpClass(cls):
testClient = super(TestLiveStorageMigration, cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.hypervisor = cls.testClient.getHypervisorInfo()
# Get Zone, Domain and templates
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient, testClient.getZoneForTests())
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata["ostype"])
cls._cleanup = []
if cls.hypervisor.lower() in ["kvm", "lxc"]:
raise unittest.SkipTest(
"Live Storage migration not supported on %s" %
cls.hypervisor)
try:
cls.pools = StoragePool.list(cls.apiclient, zoneid=cls.zone.id)
except Exception as e:
raise unittest.SkipTest(e)
try:
# Create an account
cls.account = Account.create(
cls.apiclient,
cls.testdata["account"],
domainid=cls.domain.id
)
cls._cleanup.append(cls.account)
# Create user api client of the account
cls.userapiclient = testClient.getUserApiClient(
UserName=cls.account.name,
DomainName=cls.account.domain
)
# Create Service offering
cls.service_offering_zone1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"],
tags=ZONETAG1
)
cls._cleanup.append(cls.service_offering_zone1)
cls.service_offering_cluster1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"],
tags=CLUSTERTAG1
)
cls._cleanup.append(cls.service_offering_cluster1)
# If local storage is enabled, alter the offerings to use
# localstorage
if cls.zone.localstorageenabled:
cls.testdata["service_offering"]["storagetype"] = 'local'
cls.service_offering_local1 = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"]
)
cls._cleanup.append(cls.service_offering_local1)
# Create Disk offering
cls.disk_offering_zone1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"],
tags=ZONETAG1
)
cls._cleanup.append(cls.disk_offering_zone1)
cls.disk_offering_cluster1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"],
tags=CLUSTERTAG1
)
cls._cleanup.append(cls.disk_offering_cluster1)
# If local storage is enabled, alter the offerings to use
# localstorage
if cls.zone.localstorageenabled:
cls.testdata["disk_offering"]["storagetype"] = 'local'
cls.disk_offering_local1 = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"]
)
cls._cleanup.append(cls.disk_offering_local1)
except Exception as e:
cls.tearDownClass()
raise e
return
@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.dbclient = self.testClient.getDbConnection()
self.cleanup = []
def tearDown(self):
try:
for storagePool in self.pools:
StoragePool.update(self.apiclient, id=storagePool.id, tags="")
cleanup_resources(self.apiclient, self.cleanup)
except Exception as e:
raise Exception("Warning: Exception during cleanup : %s" % e)
return
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_01_migrate_live(self):
""" Test migrate Volume (root and data disk)
# 1. Deploy a VM on cluster wide primary storage.
# 2. Migrate root and data volume to two different storage pools
in same cluster.
"""
try:
self.pools = StoragePool.list(self.apiclient, zoneid=self.zone.id)
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "CLUSTER")) >= 3,\
"There must be at least three cluster wide\
storage pools available in the setup"
except Exception as e:
self.skipTest(e)
storagePools_to_avoid = []
# Adding tags to Storage Pools
cluster_no = 1
for storagePool in self.pools:
if storagePool.scope == "CLUSTER":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['cwps' + repr(cluster_no)])
cluster_no += 1
# Step 1
# Create VM on CWPS
vm_cluster = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume
root_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
# Create DATA Volume on Cluster Wide Storage
data_volume_clust_1 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust_1.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust_1
)
data_disk_1_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust_1.id
)
data_volume_1_cluster = data_disk_1_volumes_cluster_list[0]
# Step 2
# Migrate ROOT Volume from CWPS to other CWPS
checksum_random_root_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=root_volume_cluster,
disk_type="rootdiskdevice")
# Get Destnation Pool
# Avoid storage Pool on which ROOT disk exists
storagePools_to_avoid = [root_volume_cluster.storage]
destinationPool_for_root_disk = GetDestinationPool(
self,
storagePools_to_avoid,
"CLUSTER")
# Migrate
MigrateDataVolume(
self,
root_volume_cluster,
destinationPool_for_root_disk,
islive=True)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_cluster,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
# Migrate DATA Volume from CWPS to other CWPS
checksum_random_data_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_volume_1_cluster,
disk_type="datadiskdevice_1")
# Get Destnation Pool
# Avoid storage Pool allocated for ROOT disk, and Pool on which DATA
# disk1 exists
storagePools_to_avoid = [
data_volume_1_cluster.storage,
destinationPool_for_root_disk.name]
destinationPool_for_data_disk1 = GetDestinationPool(
self,
storagePools_to_avoid,
"CLUSTER")
# Migrate
MigrateDataVolume(
self,
data_volume_1_cluster,
destinationPool_for_data_disk1,
islive=True)
# Check VM State is Running
self.assertEqual(
vm_cluster.state,
"Running",
"Check VM State is running or not.")
vm_cluster.detach_volume(
self.userapiclient,
data_volume_clust_1
)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volume_1_cluster
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volume_1_cluster)
self.new_virtual_machine.reboot(self.apiclient)
# Destroy and expunge VM and data disk
vm_cluster.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_cluster.id
), None, "VM list should be empty")
# Delete volume:
data_volume_clust_1.delete(self.apiclient)
# Verify associated disks are deleted
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_clust_1.id,
), None, "Volume list should be empty")
self.assertEqual(
Volume.list(
self.apiclient,
id=root_volume_cluster.id,
), None, "Volume list should be empty")
return
@unittest.skip(
"Requires setup with 2 pods - Each pod having 2 clusters. \
Yet to be tested")
@attr(tags=["advanced", "basic"], required_hardware="true")
def test_02_migration_live_different_pods(self):
""" Test migrate Volume (root and data disk)
# 1. Deploy a VM on cluster wide primary storage.
# 2. Migrate root and data volume to two different storage pools
in same cluster.
"""
try:
self.pools = StoragePool.list(self.apiclient, zoneid=self.zone.id)
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "ZONE")) >= 2,\
"There must be at least two zone wide\
storage pools available in the setup"
assert len(list(storagePool for storagePool in self.pools
if storagePool.scope == "CLUSTER")) >= 3,\
"There must be at least two cluster wide\
storage pools available in the setup"
except Exception as e:
self.skipTest(e)
storagePools_to_avoid = []
# Adding tags to Storage Pools
cluster_no = 1
zone_no = 1
self.debug("Storage Pools: %s" % self.pools)
for storagePool in self.pools:
if storagePool.scope == "ZONE":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['zwps' + repr(zone_no)])
zone_no += 1
elif storagePool.scope == "CLUSTER":
StoragePool.update(
self.apiclient,
id=storagePool.id,
tags=['cwps' + repr(cluster_no)])
cluster_no += 1
# Step 1
# Create VM on CWPS
vm_cluster = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_cluster1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume
root_volumes_cluster_list = list_volumes(
self.apiclient,
virtualmachineid=vm_cluster.id,
type='ROOT',
listall=True
)
root_volume_cluster = root_volumes_cluster_list[0]
# Create DATA Volume on Cluster Wide Storage
data_volume_clust_1 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust_1.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust_1
)
data_disk_1_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust_1.id
)
data_volume_1_cluster = data_disk_1_volumes_cluster_list[0]
# Step 2
# Migrate ROOT Volume from CWPS to other CWPS
checksum_random_root_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=root_volume_cluster,
disk_type="rootdiskdevice")
# Get Destnation Pool
# Avoid storage Pool on which ROOT disk exists
storagePools_to_avoid = [root_volume_cluster.storage]
destinationPool_for_root_disk = GetDestinationPool(
self,
storagePools_to_avoid,
"CLUSTER")
# Migrate
MigrateDataVolume(
self,
root_volume_cluster,
destinationPool_for_root_disk,
islive=True)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_cluster,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
# Migrate DATA Volume from CWPS to other CWPS
checksum_random_data_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_volume_1_cluster,
disk_type="datadiskdevice_1")
# Get Destnation Pool
# Avoid storage Pool allocated for ROOT disk, and Pool on which DATA
# disk1 exists
storagePools_to_avoid = [
data_volume_1_cluster.storage,
destinationPool_for_root_disk.name]
destinationPool_for_data_disk1 = GetDestinationPool(
self,
storagePools_to_avoid,
"CLUSTER")
# Migrate
MigrateDataVolume(
self,
data_volume_1_cluster,
destinationPool_for_data_disk1,
islive=True)
# Check VM State is Running
self.assertEqual(
vm_cluster.state,
"Running",
"Check VM State is running or not.")
vm_cluster.detach_volume(
self.userapiclient,
data_volume_clust_1
)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volume_1_cluster
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volume_1_cluster)
self.new_virtual_machine.reboot(self.apiclient)
# Add disk 2
data_volume_clust_2 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_cluster1.id
)
self.debug("Created volume with ID: %s" % data_volume_clust_2.id)
vm_cluster.attach_volume(
self.userapiclient,
data_volume_clust_2
)
data_disk_2_volumes_cluster_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_clust_2.id
)
data_volume_2_cluster = data_disk_2_volumes_cluster_list[0]
# Add data to second data disk
checksum_random_data_cluster = createChecksum(
service=self.testdata,
virtual_machine=vm_cluster,
disk=data_volume_2_cluster,
disk_type="datadiskdevice_2")
# TO-DO Migration
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volume_2_cluster
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_cluster,
disk_type="datadiskdevice_2",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volume_2_cluster)
self.new_virtual_machine.reboot(self.apiclient)
# TO-DO: Create Snapshot, Migrate and Restore Snapshot
# But Restore snapshot to previous stage
# is currently not working, need to investigate
# Step 3
# Create VM on ZWPS
vm_zone = VirtualMachine.create(
self.userapiclient,
self.testdata["small"],
templateid=self.template.id,
accountid=self.account.name,
domainid=self.account.domainid,
serviceofferingid=self.service_offering_zone1.id,
zoneid=self.zone.id,
mode=self.zone.networktype
)
# Get ROOT Volume Id
root_volumes_zone_list = list_volumes(
self.apiclient,
virtualmachineid=vm_zone.id,
type='ROOT',
listall=True
)
root_volume_zone = root_volumes_zone_list[0]
# Create DATA Volume on ZWPS
data_volume_zone = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering_zone1.id
)
self.debug("Created volume with ID: %s" % data_volume_zone.id)
data_volumes_zone_list = Volume.list(
self.userapiclient,
listall=self.testdata["listall"],
id=data_volume_zone.id
)
vm_zone.attach_volume(
self.userapiclient,
data_volumes_zone_list[0]
)
# Step 4
# Migrate ROOT Volume from ZWPS to other ZWPS
checksum_random_root_zone = createChecksum(
service=self.testdata,
virtual_machine=vm_zone,
disk=root_volume_zone,
disk_type="rootdiskdevice")
destinationPool = GetDestinationPool(self, root_volume_zone, "ZONE")
MigrateRootVolume(self, vm_zone, destinationPool)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_zone,
disk_type="rootdiskdevice",
virt_machine=vm_zone
)
# Try to Migrate ROOT Volume from ZWPS to Cluster wide Storage
destinationPool = GetDestinationPool(self, root_volume_zone, "CLUSTER")
MigrateRootVolume(
self,
vm_zone,
destinationPool,
expectexception=True)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_root_zone,
disk_type="rootdiskdevice",
virt_machine=vm_cluster
)
# DATA Disk
checksum_random_data_zone = createChecksum(
service=self.testdata,
virtual_machine=vm_zone,
disk=data_volumes_zone_list[0],
disk_type="datadiskdevice_1")
# Migrate DATA Volume from ZWPS to other ZWPS
destinationPool = GetDestinationPool(
self,
data_volumes_zone_list[0],
"ZONE")
MigrateDataVolume(self, data_volumes_zone_list[0], destinationPool)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_zone_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_zone,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_zone_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Try to Migrate DATA Volume from ZWPS to Cluster wide Storage
destinationPool = GetDestinationPool(self, data_volume_zone, "CLUSTER")
MigrateDataVolume(
self,
data_volume_zone,
destinationPool,
expectexception=True)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_zone_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_zone,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_zone_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Try to Migrate DATA Volume from ZWPS to Cluster wide Storage
destinationPool = GetDestinationPool(self, data_volume_zone, "CLUSTER")
MigrateDataVolume(
self,
data_volume_zone,
destinationPool,
expectexception=True)
self.new_virtual_machine.attach_volume(
self.apiclient,
data_volumes_zone_list[0]
)
# Rebooting is required so that newly attached disks are detected
self.new_virtual_machine.reboot(self.apiclient)
compareChecksum(
self.apiclient,
service=self.testdata,
original_checksum=checksum_random_data_zone,
disk_type="datadiskdevice_1",
virt_machine=self.new_virtual_machine
)
self.new_virtual_machine.detach_volume(
self.apiclient,
data_volumes_zone_list[0])
self.new_virtual_machine.reboot(self.apiclient)
# Destroy and expunge VM and data disk
vm_zone.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_cluster.id
), None, "VM list should be empty")
# Delete volume:
data_volume_zone.delete(self.apiclient)
# Verify associated disks are deleted
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_zone.id,
), None, "Volume list should be empty")
self.assertEqual(
Volume.list(
self.apiclient,
id=root_volume_zone.id,
), None, "Volume list should be empty")
# TO-DO: Local Storage
# Destroy and expunge VM and data disk
vm_cluster.delete(self.apiclient)
self.assertEqual(
VirtualMachine.list(
self.apiclient,
id=vm_cluster.id
), None, "VM list should be empty")
# Delete volume:
data_volume_clust_1.delete(self.apiclient)
data_volume_clust_2.delete(self.apiclient)
# Verify associated disks are deleted
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_clust_1.id,
), None, "Volume list should be empty")
self.assertEqual(
Volume.list(
self.apiclient,
id=data_volume_clust_2.id,
), None, "Volume list should be empty")
self.assertEqual(
Volume.list(
self.apiclient,
id=root_volume_cluster.id,
), None, "Volume list should be empty")
return
def MigrateVmWithVolume(self, vm, destinationHost, volumes, pools):
"""
This method is used to migrate a vm and its volumes using migrate virtual machine with volume API
INPUTS:
1. vm -> virtual machine object
2. destinationHost -> the host to which VM will be migrated
3. volumes -> list of volumes which are to be migrated
4. pools -> list of destination pools
"""
vol_pool_map = {}
for vol, pool in zip(volumes, pools):
vol_pool_map.update({vol.id: pool.id})
vm.migrate_vm_with_volume(
self.apiclient,
hostid=destinationHost.id,
migrateto=vol_pool_map
)
vm.getState(
self.apiclient,
"Running"
)
# check for the VM's host and volume's storage post migration
migrated_vm_response = list_virtual_machines(self.apiclient, id=vm.id)
self.assertEqual(
isinstance(migrated_vm_response, list),
True,
"Check list virtual machines response for valid list"
)
self.assertEqual(
migrated_vm_response[0].hostid,
destinationHost.id,
"VM did not migrate to a specified host"
)
for vol, pool in zip(volumes, pools):
migrated_volume_response = list_volumes(
self.apiclient,
virtualmachineid=migrated_vm_response[0].id,
name=vol.name,
listall=True)
self.assertEqual(
isinstance(migrated_volume_response, list),
True,
"Check list virtual machines response for valid list"
)
self.assertEqual(
migrated_volume_response[0].storageid,
pool.id,
"Volume did not migrate to a specified pool"
)
self.assertEqual(
str(migrated_volume_response[0].state).lower(),
'ready',
"Check migrated volume is in Ready state"
)
"""
#Take VM snapshot to check data integrity
try :
vm_snapshot = VmSnapshot.create(self.apiclient, vmid = migrated_vm_response[0].id)
except Exception as e:
raise Exception("Warning: Exception during VM snapshot creation : %s" % e)
#Delete the snapshot
try :
VmSnapshot.deleteVMSnapshot(self.apiclient, vmsnapshotid = vm_snapshot.id)
except Exception as e:
raise Exception("Warning: Exception during VM snapshot creation : %s" % e)
"""
return migrated_vm_response[0]
def MigrateVm(self, vm, destinationHost):
"""
This method is to migrate a VM using migrate virtual machine API
"""
vm.migrate(
self.apiclient,
hostid=destinationHost.id,
)
vm.getState(
self.apiclient,
"Running"
)
# check for the VM's host and volume's storage post migration
migrated_vm_response = list_virtual_machines(self.apiclient, id=vm.id)
self.assertEqual(
isinstance(migrated_vm_response, list),
True,
"Check list virtual machines response for valid list"
)
self.assertEqual(
migrated_vm_response[0].hostid,
destinationHost.id,
"VM did not migrate to a specified host"
)
return migrated_vm_response[0]
def get_destination_pools_hosts(self, vm):
"""
Get destination Pools for all volumes and destination Host for the VM
This method is use in case we use the API migrate volume with storage
"""
destinationPools = []
vol_list = list_volumes(
self.apiclient,
virtualmachineid=vm.id,
listall=True)
# For each volume get destination pool
for vol in vol_list:
pool = GetDestinationPool(self, vol.storage, "CLUSTER")
destinationPools.append(pool)
# Get destination host
destinationHost = self.GetDestinationHost(vm.hostid)
return destinationHost, destinationPools, vol_list
def check_files(self, vm, destinationHost):
"""
Check for VMX and VMDK files
INPUTS :
1. vm -> The Virtual Machine object
2. destinationHost -> The host to which we want to migrate the VM
"""
# list volumes and their pools
# Here we list all the volumes of the VM , then login to the destination host
# and check for vmx and vmdk files in the storage
vm_volumes = list_volumes(
self.apiclient,
virtualmachineid=vm.id,
listall=True)
print(vm_volumes)
for vol in vm_volumes:
spool = list_storage_pools(self.apiclient, id=vol.storageid)
split_path = spool[0].path.split("/")
pool_path = split_path[2]
sshclient = SshClient(
host=destinationHost.ipaddress,
port=22,
user="root",
passwd="freebsd")
pool_data_vmdk = sshclient.execute(
"ls /vmfs/volumes/" +
pool_path +
"/" +
vm.instancename +
"| grep vmdk")
pool_data_vmx = sshclient.execute(
"ls /vmfs/volumes/" +
pool_path +
"/" +
vm.instancename +
"| grep vmx")
if(pool_data_vmx):
vmx_file = vm.instancename + ".vmx"
if vol.type == "ROOT":
self.assertIn(
vmx_file,
pool_data_vmx,
"The VMX files are missing"
)
if(pool_data_vmdk):
vmdk_file1 = vol.path + ".vmdk"
vmdk_file2 = vol.path + "-flat.vmdk"
self.assertIn(
vmdk_file1,
pool_data_vmdk,
"The VMDK files are missing"
)
self.assertIn(
vmdk_file2,
pool_data_vmdk,
"The VMDK flat files are missing"
)
return
class TestStorageLiveMigrationVmware(cloudstackTestCase):
@classmethod
def setUpClass(cls):
testClient = super(
TestStorageLiveMigrationVmware,
cls).getClsTestClient()
cls.apiclient = testClient.getApiClient()
cls.testdata = testClient.getParsedTestDataConfig()
cls.hypervisor = cls.testClient.getHypervisorInfo()
# Get Zone, Domain and templates
cls.domain = get_domain(cls.apiclient)
cls.zone = get_zone(cls.apiclient, testClient.getZoneForTests())
cls.template = get_template(
cls.apiclient,
cls.zone.id,
cls.testdata["ostype"])
cls._cleanup = []
cls.unsupportedHypervisor = False
cls.NoResource = False
if cls.hypervisor.lower() not in [
"vmware"]:
cls.unsupportedHypervisor = True
return
# Get Hosts in the cluster and iscsi/vmfs storages for that cluster
iscsi_pools = []
try:
list_vmware_clusters = list_clusters(
cls.apiclient,
hypervisor="vmware")
except Exception as e:
cls.NoResource = True
return
assert validateList(list_vmware_clusters)[0] == PASS
if len(list_vmware_clusters) < 1:
cls.NoResource = True
return
else:
for cluster in list_vmware_clusters:
try:
list_esx_hosts = list_hosts(
cls.apiclient,
clusterid=cluster.id)
except Exception as e:
cls.NoResource = True
return
assert validateList(list_esx_hosts)[0] == PASS
if len(list_esx_hosts) > 1:
try:
list_storage = list_storage_pools(
cls.apiclient,
clusterid=cluster.id)
except Exception as e:
cls.NoResource = True
return
assert validateList(list_storage)[0] == PASS
for storage in list_storage:
if storage.type == "VMFS":
iscsi_pools.append(storage)
if len(iscsi_pools) > 1:
my_cluster_id = cluster.id
break
else:
iscsi_pools = []
if len(iscsi_pools) < 2:
cls.NoResource = True
return
cls.hosts = list_esx_hosts
cls.pools = list_storage
# Create an account
cls.account = Account.create(
cls.apiclient,
cls.testdata["account"],
domainid=cls.domain.id
)
cls._cleanup.append(cls.account)
# Create Service offering
cls.service_offering = ServiceOffering.create(
cls.apiclient,
cls.testdata["service_offering"]
)
cls._cleanup.append(cls.service_offering)
# Create Disk offering
cls.disk_offering = DiskOffering.create(
cls.apiclient,
cls.testdata["disk_offering"]
)
# Create disk offering for resize
cls.resized_disk_offering = DiskOffering.create(
cls.apiclient,
cls.testdata["resized_disk_offering"]
)
cls._cleanup.append(cls.disk_offering)
cls._cleanup.append(cls.resized_disk_offering)
return
@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.dbclient = self.testClient.getDbConnection()
if self.unsupportedHypervisor or self.NoResource:
self.skipTest("Skipping test because unsupported hypervisor\
%s" % self.hypervisor)
self.cleanup = []
def tearDown(self):
try:
for storagePool in self.pools:
StoragePool.update(self.apiclient, id=storagePool.id, tags="")
cleanup_resources(self.apiclient, self.cleanup)
except Exception as e:
raise Exception("Warning: Exception during cleanup : %s" % e)
return
def deploy_virtual_machine(self, service_offering_id, vm):
"""
Function to Deploy VMs
"""
virtual_machine = VirtualMachine.create(
self.apiclient,
self.testdata[vm],
accountid=self.account.name,
zoneid=self.zone.id,
domainid=self.account.domainid,
serviceofferingid=service_offering_id,
templateid=self.template.id,
)
virtual_machine.getState(
self.apiclient,
"Running"
)
return virtual_machine
def GetDestinationHost(self, hostsToavoid):
"""
This method gives us the destination host to which VM will be migrated
It takes the source host i.e. hostsToavoid as input
"""
destinationHost = None
for host in self.hosts:
if host.id not in hostsToavoid:
destinationHost = host
break
return destinationHost
@attr(
tags=[
"advanced",
"basic",
"vmware",
"vmfs"],
required_hardware="True")
def test_01_migrate_root_and_data_disk_live(self):
"""
Migrate VMs/Volumes on VMware with VMFS storage
"""
# List clusters and check if they have multiple hosts
# and multiple storages
# check if they storages are VMFS type
self.debug("---------------This is the test no 1--------------")
"""
Create a VM, live migrate the VM
"""
vm = "virtual_machine2"
virtual_machine_1 = self.deploy_virtual_machine(
self.service_offering.id,
vm)
# Get destination host
destinationHost = self.GetDestinationHost(virtual_machine_1.hostid)
# Migrate the VM
vm = MigrateVm(self, virtual_machine_1, destinationHost)
# self.check_files(vm,destinationHost)
self.debug("---------------This is the test no 2--------------")
"""
Migrate the ROOT Volume
"""
# Get ROOT volume and destination pool
vol_list = list_volumes(
self.apiclient,
virtualmachineid=vm.id,
type="ROOT",
listall=True)
root_vol = vol_list[0]
destinationPool = GetDestinationPool(self, root_vol.storage, "CLUSTER")
# Migrate ROOT volume
islive = True
MigrateDataVolume(self, root_vol, destinationPool, islive)
check_files(self, vm, destinationHost)
self.debug("---------------This is the test no 3--------------")
"""
Migrate the VM and ROOT volume
"""
# Get all volumes to be migrated
destinationHost, destinationPools, vol_list = get_destination_pools_hosts(
self, vm)
vm = MigrateVmWithVolume(
self,
virtual_machine_1,
destinationHost,
vol_list,
destinationPools)
check_files(self, vm, destinationHost)
self.debug("---------------This is the test no 4--------------")
"""
Add a data disk and migrate vm, data disk and root disk
"""
data_disk_1 = Volume.create(
self.apiclient,
self.testdata["volume"],
zoneid=self.zone.id,
account=self.account.name,
domainid=self.account.domainid,
diskofferingid=self.disk_offering.id
)
self.debug("Created volume with ID: %s" % data_disk_1.id)
virtual_machine_1.attach_volume(
self.apiclient,
data_disk_1
)
destinationHost, destinationPools, vol_list = get_destination_pools_hosts(
self, vm)
vm = MigrateVmWithVolume(
self,
virtual_machine_1,
destinationHost,
vol_list,
destinationPools)
check_files(self, vm, destinationHost)
self.debug("---------------This is the test no 5--------------")
"""
Upload a Volume, Attach it to the VM, Migrate all the volumes and VM.
"""
# upload a volume
self.testdata["configurableData"]["upload_volume"]["format"] = "OVA"
self.testdata["configurableData"]["upload_volume"][
"url"] = "http://nfs1.lab.vmops.com/templates/burbank-systemvm-08012012.ova"
upload_volume = Volume.upload(
self.apiclient,
self.testdata["configurableData"]["upload_volume"],
account=self.account.name,
domainid=self.domain.id,
zoneid=self.zone.id
)
upload_volume.wait_for_upload(self.apiclient)
virtual_machine_1.attach_volume(
self.apiclient,
upload_volume
)
destinationHost, destinationPools, vol_list = get_destination_pools_hosts(
self, vm)
vm = MigrateVmWithVolume(
self,
virtual_machine_1,
destinationHost,
vol_list,
destinationPools)
check_files(self, vm, destinationHost)
self.debug("---------------This is the test no 6--------------")
"""
Create snapshots on all the volumes, Migrate all the volumes and VM.
"""
# Get ROOT Volume
vol_for_snap = list_volumes(
self.apiclient,
virtualmachineid=vm.id,
listall=True)
for vol in vol_for_snap:
snapshot = Snapshot.create(
self.apiclient,
volume_id=vol.id
)
snapshot.validateState(
self.apiclient,
snapshotstate="backedup",
)
# Migrate all volumes and VMs
destinationHost, destinationPools, vol_list = get_destination_pools_hosts(
self, vm)
vm = MigrateVmWithVolume(
self,
virtual_machine_1,
destinationHost,
vol_list,
destinationPools)
check_files(self, vm, destinationHost)
self.debug("---------------This is the test no 7--------------")
"""
Resize the data volume , Migrate all the volumes and VM.
"""
data_disk_1.resize(
self.apiclient,
diskofferingid=self.resized_disk_offering.id
)
# Migrate all volumes and VMs
destinationHost, destinationPools, vol_list = get_destination_pools_hosts(
self, vm)
vm = MigrateVmWithVolume(
self,
virtual_machine_1,
destinationHost,
vol_list,
destinationPools)
check_files(self, vm, destinationHost)
self.debug("---------------This is the test no 8--------------")
"""
Restore the VM , Migrate all the volumes and VM.
"""
virtual_machine_1.restore(self.apiclient)
virtual_machine_1.getState(
self.apiclient,
"Running"
)
# Migrate the VM and its volumes
destinationHost, destinationPools, vol_list = get_destination_pools_hosts(
self, vm)
vm = MigrateVmWithVolume(
self,
virtual_machine_1,
destinationHost,
vol_list,
destinationPools)
check_files(self, vm, destinationHost)