Merge "VMAX driver - copy state fix" into stable/newton

This commit is contained in:
Jenkins 2017-03-07 21:40:17 +00:00 committed by Gerrit Code Review
commit ca6e7b4974
3 changed files with 66 additions and 37 deletions

View File

@ -6200,7 +6200,14 @@ class EMCV3DriverTestCase(test.TestCase):
return_value=self.default_extraspec())
self.driver.delete_volume(self.data.test_volume_v3)
@unittest.skip("Skip until bug #1578986 is fixed")
@mock.patch.object(
emc_vmax_utils.EMCVMAXUtils,
'get_v3_default_sg_instance_name',
return_value=(None, None, EMCVMAXCommonData.default_sg_instance_name))
@mock.patch.object(
emc_vmax_utils.EMCVMAXUtils,
'is_clone_licensed',
return_value=True)
@mock.patch.object(
emc_vmax_common.EMCVMAXCommon,
'_get_pool_and_storage_system',
@ -6210,15 +6217,11 @@ class EMCV3DriverTestCase(test.TestCase):
'get_volume_type_extra_specs',
return_value={'volume_backend_name': 'V3_BE'})
def test_create_snapshot_v3_success(
self, mock_type, mock_pool):
self, mock_type, mock_pool, mock_licence, mock_sg):
common = self.driver.common
common.provisionv3.utils.get_v3_default_sg_instance_name = mock.Mock(
return_value=(None, None, self.data.default_sg_instance_name))
common.utils.is_clone_licensed = (
mock.Mock(return_value=True))
common._initial_setup = mock.Mock(
return_value=self.default_extraspec())
self.driver.create_snapshot(self.data.test_snapshot_v3)
with mock.patch.object(common, '_initial_setup',
return_value=self.default_extraspec()):
self.driver.create_snapshot(self.data.test_snapshot_v3)
@mock.patch.object(
volume_types,
@ -6230,7 +6233,18 @@ class EMCV3DriverTestCase(test.TestCase):
return_value=self.default_extraspec())
self.driver.delete_snapshot(self.data.test_snapshot_v3)
@unittest.skip("Skip until bug #1578986 is fixed")
@mock.patch.object(
emc_vmax_utils.EMCVMAXUtils,
'get_v3_default_sg_instance_name',
return_value=(None, None, EMCVMAXCommonData.default_sg_instance_name))
@mock.patch.object(
emc_vmax_common.EMCVMAXCommon,
'_get_or_create_storage_group_v3',
return_value=EMCVMAXCommonData.default_sg_instance_name)
@mock.patch.object(
emc_vmax_utils.EMCVMAXUtils,
'is_clone_licensed',
return_value=True)
@mock.patch.object(
emc_vmax_utils.EMCVMAXUtils,
'compare_size',
@ -6248,8 +6262,11 @@ class EMCV3DriverTestCase(test.TestCase):
'volume_get',
return_value=EMCVMAXCommonData.test_source_volume)
def test_create_cloned_volume_v3_success(
self, mock_volume_db, mock_type, mock_pool, mock_compare):
self.data.test_volume_v3['volume_name'] = "vmax-1234567"
self, mock_volume_db, mock_type, mock_pool, mock_compare,
mock_licence, mock_sg, mock_sg_name):
sourceVol = self.data.test_volume_v3.copy()
sourceVol['volume_name'] = "vmax-1234567"
sourceVol['size'] = 100
cloneVol = {}
cloneVol['name'] = 'vol1'
cloneVol['id'] = '10'
@ -6262,17 +6279,16 @@ class EMCV3DriverTestCase(test.TestCase):
cloneVol['NumberOfBlocks'] = 100
cloneVol['BlockSize'] = self.data.block_size
cloneVol['host'] = self.data.fake_host_v3
cloneVol['size'] = 1
cloneVol['size'] = 100
common = self.driver.common
common.utils.is_clone_licensed = (
mock.Mock(return_value=True))
common._initial_setup = mock.Mock(
return_value=self.default_extraspec())
common._get_or_create_storage_group_v3 = mock.Mock(
return_value = self.data.default_sg_instance_name)
common.provisionv3.utils.get_v3_default_sg_instance_name = mock.Mock(
return_value=(None, None, self.data.default_sg_instance_name))
self.driver.create_cloned_volume(cloneVol, self.data.test_volume_v3)
conn = FakeEcomConnection()
sourceInstance = (
conn.EnumerateInstanceNames("EMC_StorageVolume")[0])
with mock.patch.object(common, '_initial_setup',
return_value=self.default_extraspec()):
with mock.patch.object(common, '_find_lun',
return_value=sourceInstance):
self.driver.create_cloned_volume(cloneVol, sourceVol)
@mock.patch.object(
emc_vmax_common.EMCVMAXCommon,
@ -7703,7 +7719,11 @@ class EMCVMAXProvisionV3Test(test.TestCase):
extraSpecs)
self.assertEqual(self.data.default_sg_instance_name, newstoragegroup)
def test_create_element_replica(self):
@mock.patch.object(
emc_vmax_utils.EMCVMAXUtils,
'get_v3_default_sg_instance_name',
return_value=(None, None, EMCVMAXCommonData.default_sg_instance_name))
def test_create_element_replica(self, mock_sg):
provisionv3 = self.driver.common.provisionv3
conn = FakeEcomConnection()
repServiceInstanceName = {
@ -7718,8 +7738,6 @@ class EMCVMAXProvisionV3Test(test.TestCase):
conn.EnumerateInstanceNames("EMC_StorageVolume")[0])
syncType = 7
cloneName = 'new_ss'
provisionv3.utils.get_v3_default_sg_instance_name = mock.Mock(
return_value=(None, None, self.data.default_sg_instance_name))
rc, job = provisionv3.create_element_replica(
conn, repServiceInstanceName, cloneName, syncType, sourceInstance,
extraSpecs)

View File

@ -3914,6 +3914,7 @@ class EMCVMAXCommon(object):
operation = self.utils.get_num(DISSOLVE_SNAPVX, '16')
rsdInstance = None
targetInstance = None
copyState = None
if isSnapshot:
rsdInstance = self.utils.set_target_element_supplier_in_rsd(
self.conn, repServiceInstanceName, SNAPVX_REPLICATION_TYPE,
@ -3921,12 +3922,14 @@ class EMCVMAXCommon(object):
else:
targetInstance = self._create_duplicate_volume(
sourceInstance, cloneName, extraSpecs)
copyState = self.utils.get_num(4, '16')
try:
_rc, job = (
self.provisionv3.create_element_replica(
self.conn, repServiceInstanceName, cloneName, syncType,
sourceInstance, extraSpecs, targetInstance, rsdInstance))
sourceInstance, extraSpecs, targetInstance, rsdInstance,
copyState))
except Exception:
LOG.warning(_LW(
"Clone failed on V3. Cleaning up the target volume. "

View File

@ -234,7 +234,7 @@ class EMCVMAXProvisionV3(object):
def create_element_replica(
self, conn, repServiceInstanceName,
cloneName, syncType, sourceInstance, extraSpecs,
targetInstance=None, rsdInstance=None):
targetInstance=None, rsdInstance=None, copyState=None):
"""Make SMI-S call to create replica for source element.
:param conn: the connection to the ecom server
@ -284,7 +284,7 @@ class EMCVMAXProvisionV3(object):
rc, job = self._create_element_replica_extra_params(
conn, repServiceInstanceName, cloneName, syncType,
sourceInstance, targetInstance, rsdInstance,
sgInstanceName)
sgInstanceName, copyState=copyState)
if rc != 0:
rc, errordesc = self.utils.wait_for_job_complete(conn, job,
@ -309,7 +309,8 @@ class EMCVMAXProvisionV3(object):
def _create_element_replica_extra_params(
self, conn, repServiceInstanceName, cloneName, syncType,
sourceInstance, targetInstance, rsdInstance, sgInstanceName):
sourceInstance, targetInstance, rsdInstance, sgInstanceName,
copyState=None):
"""CreateElementReplica using extra parameters.
:param conn: the connection to the ecom server
@ -332,13 +333,6 @@ class EMCVMAXProvisionV3(object):
SourceElement=sourceInstance.path,
TargetElement=targetInstance.path,
ReplicationSettingData=rsdInstance)
elif targetInstance:
rc, job = conn.InvokeMethod(
'CreateElementReplica', repServiceInstanceName,
ElementName=cloneName,
SyncType=syncType,
SourceElement=sourceInstance.path,
TargetElement=targetInstance.path)
elif rsdInstance:
rc, job = conn.InvokeMethod(
'CreateElementReplica', repServiceInstanceName,
@ -347,7 +341,21 @@ class EMCVMAXProvisionV3(object):
SourceElement=sourceInstance.path,
ReplicationSettingData=rsdInstance,
Collections=[sgInstanceName])
elif targetInstance and copyState:
rc, job = conn.InvokeMethod(
'CreateElementReplica', repServiceInstanceName,
ElementName=cloneName,
SyncType=syncType,
SourceElement=sourceInstance.path,
TargetElement=targetInstance.path,
WaitForCopyState=copyState)
elif targetInstance:
rc, job = conn.InvokeMethod(
'CreateElementReplica', repServiceInstanceName,
ElementName=cloneName,
SyncType=syncType,
SourceElement=sourceInstance.path,
TargetElement=targetInstance.path)
return rc, job
def break_replication_relationship(