use of com.emc.storageos.volumecontroller.impl.utils.ControllerOperationValuesWrapper in project coprhd-controller by CoprHD.
the class VPlexBlockServiceApiImpl method changeVolumeVirtualPool.
/**
* {@inheritDoc}
*/
@Override
public TaskList changeVolumeVirtualPool(List<Volume> volumes, VirtualPool vpool, VirtualPoolChangeParam vpoolChangeParam, String taskId) throws InternalException {
TaskList taskList = new TaskList();
StringBuffer notSuppReasonBuff = new StringBuffer();
VirtualPool volumeVirtualPool = _dbClient.queryObject(VirtualPool.class, volumes.get(0).getVirtualPool());
if (VirtualPoolChangeAnalyzer.isSupportedPathParamsChange(volumes.get(0), volumeVirtualPool, vpool, _dbClient, notSuppReasonBuff) || VirtualPoolChangeAnalyzer.isSupportedAutoTieringPolicyAndLimitsChange(volumes.get(0), volumeVirtualPool, vpool, _dbClient, notSuppReasonBuff)) {
taskList = createTasksForVolumes(vpool, volumes, taskId);
checkCommonVpoolUpdates(volumes, vpool, taskId);
return taskList;
}
// Check if any of the volumes passed is a VPLEX volume
// in a VPLEX CG with corresponding local consistency
// group(s) for the backend volumes.
Volume changeVPoolVolume = isVPlexVolumeInCgWithLocalType(volumes);
if (changeVPoolVolume != null) {
s_logger.info("Change vpool request has volumes in VPLEX CG with backing local CGs");
// If any of the volumes is a CG and if this is a data
// migration of the volumes, then the volumes passed must
// contain all the volumes in that CG.
VirtualPool currentVPool = _dbClient.queryObject(VirtualPool.class, changeVPoolVolume.getVirtualPool());
VirtualPoolChangeOperationEnum vpoolChange = VirtualPoolChangeAnalyzer.getSupportedVPlexVolumeVirtualPoolChangeOperation(changeVPoolVolume, currentVPool, vpool, _dbClient, new StringBuffer());
if ((vpoolChange != null) && (vpoolChange == VirtualPoolChangeOperationEnum.VPLEX_DATA_MIGRATION)) {
s_logger.info("Vpool change is a data migration");
ControllerOperationValuesWrapper operationsWrapper = new ControllerOperationValuesWrapper();
operationsWrapper.put(ControllerOperationValuesWrapper.MIGRATION_SUSPEND_BEFORE_COMMIT, vpoolChangeParam.getMigrationSuspendBeforeCommit());
operationsWrapper.put(ControllerOperationValuesWrapper.MIGRATION_SUSPEND_BEFORE_DELETE_SOURCE, vpoolChangeParam.getMigrationSuspendBeforeDeleteSource());
List<Volume> volumesNotInRG = new ArrayList<Volume>();
taskList = migrateVolumesInReplicationGroup(volumes, vpool, volumesNotInRG, null, operationsWrapper);
// Migrate volumes not in Replication Group as single volumes
if (!volumesNotInRG.isEmpty()) {
// Get the migration descriptors
List<VolumeDescriptor> descriptors = new ArrayList<VolumeDescriptor>();
for (Volume volume : volumesNotInRG) {
StorageSystem vplexStorageSystem = _dbClient.queryObject(StorageSystem.class, volume.getStorageController());
descriptors.addAll(createChangeVirtualPoolDescriptors(vplexStorageSystem, volume, vpool, taskId, null, null, operationsWrapper, true));
}
// Create the tasks
taskList.getTaskList().addAll(createTasksForVolumes(vpool, volumesNotInRG, taskId).getTaskList());
// Now we get the Orchestration controller and use it to migrate all the volumes not in a RG.
orchestrateVPoolChanges(volumesNotInRG, descriptors, taskId);
}
return taskList;
}
}
// Otherwise proceed as we normally would performing
// individual vpool changes for each volume.
String nextTaskId = taskId;
for (Volume volume : volumes) {
taskList.getTaskList().addAll(changeVolumeVirtualPool(volume.getStorageController(), volume, vpool, vpoolChangeParam, nextTaskId).getTaskList());
// Create a unique task id.
nextTaskId = UUID.randomUUID().toString();
}
return taskList;
}
use of com.emc.storageos.volumecontroller.impl.utils.ControllerOperationValuesWrapper in project coprhd-controller by CoprHD.
the class RPBlockServiceApiImpl method rpVPlexGroupedMigrations.
/**
* Calls out to the VPLEX Block Service to group any volumes in RG and migrate
* the volumes together. If there are any volumes not in RGs they are returned
* and then added to the single migration container to be migrated later.
*
* @param volumesToMigrate All volumes to migrate
* @param singleMigrations Container to keep track of single migrations
* @param type Personality type for logging
* @param logMigrations Log buffer
* @param taskList List of tasks that will be returned to user
* @param vpoolChangeParam used to determine if we should suspend on migration commit
*/
private void rpVPlexGroupedMigrations(HashMap<VirtualPool, List<Volume>> volumesToMigrate, Map<Volume, VirtualPool> singleMigrations, String type, StringBuffer logMigrations, TaskList taskList, VirtualPoolChangeParam vpoolChangeParam) {
for (Map.Entry<VirtualPool, List<Volume>> entry : volumesToMigrate.entrySet()) {
// List to hold volumes that are grouped by RG and migrated together
List<Volume> volumesInRG = new ArrayList<Volume>();
// List to hold volumes that are not grouped by RG and will be migrated as single migrations
List<Volume> volumesNotInRG = new ArrayList<Volume>();
VirtualPool migrateToVpool = entry.getKey();
List<Volume> migrateVolumes = entry.getValue();
ControllerOperationValuesWrapper operationsWrapper = new ControllerOperationValuesWrapper();
operationsWrapper.put(ControllerOperationValuesWrapper.MIGRATION_SUSPEND_BEFORE_COMMIT, vpoolChangeParam.getMigrationSuspendBeforeCommit());
operationsWrapper.put(ControllerOperationValuesWrapper.MIGRATION_SUSPEND_BEFORE_DELETE_SOURCE, vpoolChangeParam.getMigrationSuspendBeforeDeleteSource());
TaskList taskList2 = vplexBlockServiceApiImpl.migrateVolumesInReplicationGroup(migrateVolumes, migrateToVpool, volumesNotInRG, volumesInRG, operationsWrapper);
taskList.getTaskList().addAll(taskList2.getTaskList());
for (Volume volumeInRG : volumesInRG) {
logMigrations.append(String.format("\tRP+VPLEX migrate %s [%s](%s) to vpool [%s](%s) - GROUPED BY RG\n", type, volumeInRG.getLabel(), volumeInRG.getId(), migrateToVpool.getLabel(), migrateToVpool.getId()));
}
for (Volume volumeNotInRG : volumesNotInRG) {
logMigrations.append(String.format("\tRP+VPLEX migrate %s [%s](%s) to vpool [%s](%s)\n", type, volumeNotInRG.getLabel(), volumeNotInRG.getId(), migrateToVpool.getLabel(), migrateToVpool.getId()));
singleMigrations.put(volumeNotInRG, migrateToVpool);
}
}
}
use of com.emc.storageos.volumecontroller.impl.utils.ControllerOperationValuesWrapper in project coprhd-controller by CoprHD.
the class VPlexBlockServiceApiImpl method changeVolumeVirtualPool.
/**
* {@inheritDoc}
*
* @throws InternalException
*/
@Override
public TaskList changeVolumeVirtualPool(URI systemURI, Volume volume, VirtualPool vpool, VirtualPoolChangeParam vpoolChangeParam, String taskId) throws InternalException {
VirtualPool volumeVirtualPool = _dbClient.queryObject(VirtualPool.class, volume.getVirtualPool());
s_logger.info("Volume {} VirtualPool change.", volume.getId());
TaskList taskList = createTasksForVolumes(vpool, Arrays.asList(volume), taskId);
String transferSpeed = null;
ArrayList<Volume> volumes = new ArrayList<Volume>();
volumes.add(volume);
if (checkCommonVpoolUpdates(volumes, vpool, taskId)) {
return taskList;
}
// Get the storage system. This could be a vplex, vmax, or
// vnxblock, or other block storage system.
StorageSystem storageSystem = _dbClient.queryObject(StorageSystem.class, systemURI);
String systemType = storageSystem.getSystemType();
if (!DiscoveredDataObject.Type.vplex.name().equals(systemType)) {
// If it is not a VPLEX volume, then this must be an import to VPLEX.
s_logger.info("High availability VirtualPool change for array volume, importing volume VPLEX: " + volume.getLabel());
importVirtualVolume(systemURI, volume, vpool, taskId);
// Check to see if the imported volume is an SRDF source volume.
if (volume.getSrdfTargets() != null) {
StringSet srdfTargets = volume.getSrdfTargets();
for (String target : srdfTargets) {
Volume targetVolume = _dbClient.queryObject(Volume.class, URI.create(target));
URI targetVarray = targetVolume.getVirtualArray();
// Get the target virtual pool.
Map<URI, VpoolRemoteCopyProtectionSettings> protectionSettingsMap = VirtualPool.getRemoteProtectionSettings(vpool, _dbClient);
VpoolRemoteCopyProtectionSettings settings = protectionSettingsMap.get(targetVarray);
if (settings != null) {
VirtualPool targetVpool = _dbClient.queryObject(VirtualPool.class, settings.getVirtualPool());
if (NullColumnValueGetter.isNotNullValue(targetVpool.getHighAvailability()) && targetVpool.getHighAvailability().equals(VirtualPool.HighAvailabilityType.vplex_local.name())) {
String subTaskId = UUID.randomUUID().toString();
s_logger.info("Importing SRDF target to VPLEX " + targetVolume.getLabel());
Operation op = new Operation();
op.setResourceType(ResourceOperationTypeEnum.CHANGE_BLOCK_VOLUME_VPOOL);
op.setDescription("Change vpool operation");
op = _dbClient.createTaskOpStatus(Volume.class, targetVolume.getId(), subTaskId, op);
taskList.addTask(toTask(targetVolume, subTaskId, op));
importVirtualVolume(targetVolume.getStorageController(), targetVolume, targetVpool, subTaskId);
}
}
}
}
} else {
if (VirtualPoolChangeAnalyzer.isVPlexConvertToDistributed(volumeVirtualPool, vpool, new StringBuffer())) {
if (!VirtualPoolUtil.checkMatchingRemoteCopyVarraysettings(volumeVirtualPool, vpool, _dbClient)) {
s_logger.info("Incompatible Remote Copy Varray Settings");
throw BadRequestException.badRequests.changeToVirtualPoolNotSupported(volumeVirtualPool.getLabel(), "Incompatible Remote Copy Varray Settings");
}
if (vpoolChangeParam.getTransferSpeedParam() != null) {
transferSpeed = vpoolChangeParam.getTransferSpeedParam();
s_logger.info("Coversion of volume from vplex local to distributed will use the provided transfer speed {}", transferSpeed);
}
// Convert vplex_local to vplex_distributed
upgradeToDistributed(systemURI, volume, vpool, transferSpeed, taskId);
} else if (!VirtualPool.vPoolSpecifiesMirrors(volumeVirtualPool, _dbClient) && (VirtualPool.vPoolSpecifiesMirrors(vpool, _dbClient)) && VirtualPoolChangeAnalyzer.isSupportedAddMirrorsVirtualPoolChange(volume, volumeVirtualPool, vpool, _dbClient, new StringBuffer())) {
// Change Virtual pool to have continuous copies
URI originalVirtualPool = volume.getVirtualPool();
// Update the volume with the new virtual pool
volume.setVirtualPool(vpool.getId());
_dbClient.updateObject(volume);
// Update the task
String msg = format("VirtualPool changed from %s to %s for Volume %s", originalVirtualPool, vpool.getId(), volume.getId());
s_logger.info(msg);
_dbClient.createTaskOpStatus(Volume.class, volume.getId(), taskId, ResourceOperationTypeEnum.CHANGE_BLOCK_VOLUME_VPOOL);
_dbClient.ready(Volume.class, volume.getId(), taskId, msg);
} else {
// Prepare for VPlex virtual volume VirtualPool change.
// Get the varray for the virtual volume.
s_logger.info("VirtualPool change for VPlex virtual volume.");
ControllerOperationValuesWrapper operationsWrapper = new ControllerOperationValuesWrapper();
operationsWrapper.put(ControllerOperationValuesWrapper.MIGRATION_SUSPEND_BEFORE_COMMIT, vpoolChangeParam.getMigrationSuspendBeforeCommit());
operationsWrapper.put(ControllerOperationValuesWrapper.MIGRATION_SUSPEND_BEFORE_DELETE_SOURCE, vpoolChangeParam.getMigrationSuspendBeforeDeleteSource());
List<VolumeDescriptor> descriptors = createChangeVirtualPoolDescriptors(storageSystem, volume, vpool, taskId, null, null, operationsWrapper, true);
// Now we get the Orchestration controller and use it to change the virtual pool of the volumes.
orchestrateVPoolChanges(Arrays.asList(volume), descriptors, taskId);
}
}
return taskList;
}
Aggregations