diff --git a/cinder/tests/unit/volume/drivers/dell_emc/powermax/test_powermax_common.py b/cinder/tests/unit/volume/drivers/dell_emc/powermax/test_powermax_common.py index 4c6335b2b15..93eaefbd38d 100644 --- a/cinder/tests/unit/volume/drivers/dell_emc/powermax/test_powermax_common.py +++ b/cinder/tests/unit/volume/drivers/dell_emc/powermax/test_powermax_common.py @@ -1700,7 +1700,7 @@ class PowerMaxCommonTest(test.TestCase): volume_name = self.data.test_attached_volume.name # Rep Config rep_mode = 'Synchronous' - self.common.rep_config = {'mode': rep_mode} + self.common.rep_config = {'mode': rep_mode, 'metro_use_bias': True} # Extra Specs new_type = {'extra_specs': {}} src_extra_specs = self.data.extra_specs_migrate @@ -1737,8 +1737,10 @@ class PowerMaxCommonTest(test.TestCase): success = self.common._migrate_volume( array, volume, device_id, srp, slo, workload, volume_name, new_type, src_extra_specs)[0] + cleanup_specs = src_extra_specs + cleanup_specs['force_vol_add'] = True mck_cleanup.assert_called_once_with( - volume, volume_name, device_id, src_extra_specs) + volume, volume_name, device_id, cleanup_specs) mck_retype.assert_called_once_with( array, srp, volume, device_id, src_extra_specs, slo, workload, tgt_extra_specs, False) @@ -1753,8 +1755,11 @@ class PowerMaxCommonTest(test.TestCase): success = self.common._migrate_volume( array, volume, device_id, srp, slo, workload, volume_name, new_type, src_extra_specs)[0] + mck_setup_specs = src_extra_specs + mck_setup_specs[utils.METROBIAS] = self.common.rep_config[ + 'metro_use_bias'] mck_setup.assert_called_once_with( - self.data.array, volume, device_id, src_extra_specs) + self.data.array, volume, device_id, mck_setup_specs) mck_retype.assert_called_once_with( array, srp, volume, device_id, src_extra_specs, slo, workload, tgt_extra_specs, False) @@ -1779,6 +1784,8 @@ class PowerMaxCommonTest(test.TestCase): mck_setup.assert_not_called() self.assertTrue(success) + @mock.patch.object(common.PowerMaxCommon, 'setup_volume_replication', + return_value=('Status', 'Data', 'Info')) @mock.patch.object(common.PowerMaxCommon, '_retype_volume', return_value=True) @mock.patch.object(common.PowerMaxCommon, 'cleanup_lun_replication') @@ -1792,8 +1799,8 @@ class PowerMaxCommonTest(test.TestCase): @mock.patch.object(common.PowerMaxCommon, 'get_volume_metadata', return_value='') def test_migrate_volume_attachment_path( - self, mck_meta, mck_remote_retype, mck_setup, mck_inuse_retype, - mck_cleanup, mck_retype): + self, mck_meta, mck_remote_retype, mck_setup_use, mck_inuse_retype, + mck_cleanup, mck_retype, mck_setup): # Array/Volume info array = self.data.array srp = self.data.srp @@ -1820,7 +1827,7 @@ class PowerMaxCommonTest(test.TestCase): self.assertTrue(success) mck_cleanup.reset_mock() - mck_setup.reset_mock() + mck_setup_use.reset_mock() # Scenario 2: Volume not attached with mock.patch.object(self.utils, 'is_replication_enabled', @@ -1831,6 +1838,23 @@ class PowerMaxCommonTest(test.TestCase): mck_retype.assert_called_once() self.assertTrue(success) + # Scenario 3: Volume not attached, enable RDF + tgt_extra_specs = { + 'srp': srp, 'array': array, 'slo': slo, 'workload': workload, + 'interval': src_extra_specs['interval'], + 'retries': src_extra_specs['retries'], + utils.METROBIAS: True} + self.common.rep_config[utils.METROBIAS] = True + with mock.patch.object(self.utils, 'is_replication_enabled', + side_effect=[False, True]): + success = self.common._migrate_volume( + array, volume_not_attached, device_id, srp, slo, workload, + volume_not_attached_name, new_type, src_extra_specs)[0] + mck_setup.assert_called_once_with(array, volume_not_attached, + device_id, tgt_extra_specs) + mck_retype.assert_called_once() + self.assertTrue(success) + @mock.patch.object(masking.PowerMaxMasking, 'remove_and_reset_members') def test_migrate_volume_failed_get_new_sg_failed(self, mock_remove): device_id = self.data.device_id diff --git a/cinder/volume/drivers/dell_emc/powermax/common.py b/cinder/volume/drivers/dell_emc/powermax/common.py index 02b352db59f..3020fe265e5 100644 --- a/cinder/volume/drivers/dell_emc/powermax/common.py +++ b/cinder/volume/drivers/dell_emc/powermax/common.py @@ -3154,6 +3154,9 @@ class PowerMaxCommon(object): # Scenario: Rep was enabled, target VT has rep disabled, need to # disable replication if was_rep_enabled and not is_rep_enabled: + # Add force to allow volume removal from RDF enabled + # storage groups + extra_specs['force_vol_remove'] = True self.cleanup_lun_replication(volume, volume_name, device_id, extra_specs) model_update = { @@ -3163,6 +3166,9 @@ class PowerMaxCommon(object): # Scenario: Rep was not enabled, target VT has rep enabled, need to # enable replication elif not was_rep_enabled and is_rep_enabled: + metro_bias = utils.METROBIAS + if metro_bias in self.rep_config: + extra_specs[metro_bias] = self.rep_config[metro_bias] rep_status, rep_driver_data, rep_info_dict = ( self.setup_inuse_volume_replication( array, volume, device_id, extra_specs)) @@ -3197,6 +3203,10 @@ class PowerMaxCommon(object): move_target = True else: if is_rep_enabled: + metro_bias = utils.METROBIAS + if metro_bias in self.rep_config: + target_extra_specs[ + metro_bias] = self.rep_config[metro_bias] # Setup_volume_replication will put volume in correct sg rep_status, rdf_dict, __ = self.setup_volume_replication( array, volume, device_id, target_extra_specs)