use of com.emc.storageos.db.client.model.BlockMirror in project coprhd-controller by CoprHD.
the class SmisStorageDevice method doAddToReplicationGroup.
@Override
public void doAddToReplicationGroup(final StorageSystem storage, final URI consistencyGroupId, final String replicationGroupName, final List<URI> replicas, final TaskCompleter taskCompleter) throws DeviceControllerException {
// 8.0.3 will support adding replicas to replication group but the replicas should be added to the
// device masking group corresponding to the consistency group
_log.info("Adding replicas to Device Masking Group equivalent to its ReplicationGroup {}", replicationGroupName);
List<URI> replicasToAdd;
try {
if (!storage.deviceIsType(Type.vnxblock)) {
replicasToAdd = _helper.filterReplicasAlreadyPartOfReplicationGroup(storage, replicationGroupName, replicas);
if (!replicasToAdd.isEmpty()) {
CIMArgument[] inArgsAdd;
inArgsAdd = _helper.getAddVolumesToMaskingGroupInputArguments(storage, replicationGroupName, replicasToAdd, null, true);
CIMArgument[] outArgsAdd = new CIMArgument[5];
_helper.invokeMethodSynchronously(storage, _cimPath.getControllerConfigSvcPath(storage), SmisConstants.ADD_MEMBERS, inArgsAdd, outArgsAdd, null);
} else {
_log.info("Requested replicas {} are already part of the Replication Group {}, hence skipping AddMembers call..", Joiner.on(", ").join(replicas), replicationGroupName);
}
} else {
_log.info("There is no corresponding replication group for VNX mirrors and clones");
}
// persist group name/settings instance (for VMAX3) in replica objects
List<BlockObject> replicaList = new ArrayList<BlockObject>();
String settingsInst = null;
if (storage.checkIfVmax3() && URIUtil.isType(replicas.get(0), BlockSnapshot.class)) {
List<BlockSnapshot> blockSnapshots = ControllerUtils.getSnapshotsPartOfReplicationGroup(replicationGroupName, storage.getId(), _dbClient);
if (blockSnapshots != null && !blockSnapshots.isEmpty()) {
settingsInst = blockSnapshots.get(0).getSettingsInstance();
}
}
for (URI replica : replicas) {
BlockObject replicaObj = BlockObject.fetch(_dbClient, replica);
replicaObj.setReplicationGroupInstance(replicationGroupName);
// don't set CG on Clones
if (replicaObj instanceof BlockMirror || replicaObj instanceof BlockSnapshot) {
replicaObj.setConsistencyGroup(consistencyGroupId);
if (replicaObj instanceof BlockMirror) {
String groupName = ConsistencyGroupUtils.getSourceConsistencyGroupName(replicaObj, _dbClient);
CIMObjectPath syncPath = _cimPath.getGroupSynchronizedPath(storage, groupName, replicationGroupName);
((BlockMirror) replicaObj).setSynchronizedInstance(syncPath.toString());
} else if (replicaObj instanceof BlockSnapshot) {
if (settingsInst != null) {
((BlockSnapshot) replicaObj).setSettingsInstance(settingsInst);
}
}
}
replicaList.add(replicaObj);
}
_dbClient.updateAndReindexObject(replicaList);
taskCompleter.ready(_dbClient);
} catch (Exception e) {
_log.error("Problem while adding replica to device masking group :{}", consistencyGroupId, e);
if (null != replicas && !replicas.isEmpty()) {
for (URI replicaURI : replicas) {
BlockObject blockObj = _dbClient.queryObject(BlockObject.class, replicaURI);
blockObj.setReplicationGroupInstance(NullColumnValueGetter.getNullStr());
_dbClient.updateObject(blockObj);
}
}
taskCompleter.error(_dbClient, DeviceControllerException.exceptions.failedToAddMembersToReplicationGroup(replicationGroupName, storage.getLabel(), e.getMessage()));
return;
}
}
use of com.emc.storageos.db.client.model.BlockMirror in project coprhd-controller by CoprHD.
the class SmisStorageDevice method doAddToConsistencyGroup.
@Override
public void doAddToConsistencyGroup(StorageSystem storage, final URI consistencyGroupId, String replicationGroupName, final List<URI> blockObjectURIs, final TaskCompleter taskCompleter) throws DeviceControllerException {
BlockConsistencyGroup consistencyGroup = _dbClient.queryObject(BlockConsistencyGroup.class, consistencyGroupId);
Map<URI, BlockObject> uriToBlockObjectMap = new HashMap<URI, BlockObject>();
List<URI> replicas = new ArrayList<URI>();
List<URI> volumes = new ArrayList<URI>();
try {
List<BlockObject> blockObjects = new ArrayList<BlockObject>();
for (URI blockObjectURI : blockObjectURIs) {
// FIXME Performance improvement here
BlockObject blockObject = BlockObject.fetch(_dbClient, blockObjectURI);
if (blockObject != null) {
blockObjects.add(blockObject);
uriToBlockObjectMap.put(blockObjectURI, blockObject);
}
}
/**
* Request: Volume CG with volume objects OR
* Volume CG with replica objects(snap/clone/mirror)
*
* make sure that the blockObjects are of same type (Volume/Snap/Clone/Mirror)
* If Volume:
* add them to group
* If Replica (supported only for 8.0):
* If existing replicas do not have replicationGroupInstance set:
* create new RG on array with random name,
* add replicas to that RG,
* set RG name in replicationGroupInstance field for new replicas.
* Else:
* Get RG name from existing replica,
* Add new replicas to DMG with same name as RG name,
* set RG name in replicationGroupInstance field for new replicas.
*
* For all objects except Clone, set CG URI.
*/
for (BlockObject blockObject : blockObjects) {
boolean isFullCopy = false;
if (blockObject instanceof Volume) {
isFullCopy = ControllerUtils.isVolumeFullCopy((Volume) blockObject, _dbClient);
}
if (blockObject instanceof BlockSnapshot || isFullCopy || blockObject instanceof BlockMirror) {
replicas.add(blockObject.getId());
} else {
volumes.add(blockObject.getId());
}
}
// adding replicas to ReplicationGroup is supported only for 8.0
if (!storage.getUsingSmis80() && !replicas.isEmpty()) {
String errMsg = "Adding replicas to Consistency Group is not supported on 4.6.x Provider";
_log.warn(errMsg);
taskCompleter.error(_dbClient, DeviceControllerException.exceptions.failedToAddMembersToConsistencyGroup(consistencyGroup.getLabel(), consistencyGroup.fetchArrayCgName(storage.getId()), errMsg));
return;
}
if (!volumes.isEmpty() && !replicas.isEmpty()) {
String errMsg = "Mix of Volumes and Replica types is not supported";
_log.warn(errMsg);
taskCompleter.error(_dbClient, DeviceControllerException.exceptions.failedToAddMembersToConsistencyGroup(consistencyGroup.getLabel(), consistencyGroup.getCgNameOnStorageSystem(storage.getId()), errMsg));
return;
}
if (!replicas.isEmpty()) {
addReplicasToConsistencyGroup(storage, consistencyGroup, replicas, uriToBlockObjectMap);
} else if (!volumes.isEmpty()) {
// get source provider for SRDF target volumes
// target CG is created using source system provider
StorageSystem forProvider = storage;
boolean isSrdfTarget = false;
Volume vol = (Volume) uriToBlockObjectMap.get(volumes.iterator().next());
if (vol.checkForSRDF() && !NullColumnValueGetter.isNullNamedURI(vol.getSrdfParent())) {
Volume srcVolume = _dbClient.queryObject(Volume.class, vol.getSrdfParent().getURI());
forProvider = _dbClient.queryObject(StorageSystem.class, srcVolume.getStorageController());
isSrdfTarget = true;
}
// Check if the consistency group exists
boolean createCG = false;
CIMObjectPath cgPath = null;
CIMInstance cgPathInstance = null;
boolean isVPlexOrRP = consistencyGroup.checkForType(Types.VPLEX) || consistencyGroup.checkForType(Types.RP);
String groupName = ControllerUtils.generateReplicationGroupName(storage, consistencyGroup, replicationGroupName, _dbClient);
// If this is for VPlex or RP, we would create backend consistency group if it does not exist yet.
if (!consistencyGroup.created(storage.getId(), groupName)) {
if (isVPlexOrRP) {
createCG = true;
_log.info(String.format("No consistency group exists for the storage: %s", storage.getId()));
} else {
ServiceError error = DeviceControllerErrors.smis.noConsistencyGroupWithGivenName();
taskCompleter.error(_dbClient, error);
return;
}
} else {
if (!isSrdfTarget) {
StorageSystem storageSystem = findProviderFactory.withGroup(storage, groupName).find();
if (storageSystem == null) {
if (isVPlexOrRP) {
_log.info(String.format("Could not find consistency group with the name: %s", groupName));
createCG = true;
} else {
ServiceError error = DeviceControllerErrors.smis.noConsistencyGroupWithGivenName();
taskCompleter.error(_dbClient, error);
return;
}
} else {
forProvider = storageSystem;
}
}
if (!createCG && !(storage.deviceIsType(Type.vnxblock) && !consistencyGroup.getArrayConsistency())) {
cgPath = _cimPath.getReplicationGroupPath(forProvider, storage.getSerialNumber(), groupName);
cgPathInstance = _helper.checkExists(forProvider, cgPath, false, false);
// operation to error
if (cgPathInstance == null) {
taskCompleter.error(_dbClient, DeviceControllerException.exceptions.consistencyGroupNotFound(consistencyGroup.getLabel(), consistencyGroup.getCgNameOnStorageSystem(storage.getId())));
return;
}
}
}
if (createCG) {
doCreateConsistencyGroup(storage, consistencyGroupId, groupName, null);
consistencyGroup = _dbClient.queryObject(BlockConsistencyGroup.class, consistencyGroupId);
cgPath = _cimPath.getReplicationGroupPath(storage, groupName);
}
if (storage.deviceIsType(Type.vnxblock) && !consistencyGroup.getArrayConsistency()) {
// nothing need to be done on array side
_log.info("No array operation needed for VNX replication group {}", groupName);
} else {
CIMObjectPath replicationSvc = _cimPath.getControllerReplicationSvcPath(storage);
String[] blockObjectNames = _helper.getBlockObjectAlternateNames(volumes);
// Smis call to add volumes that are already available in Group, will result in error.
// Refresh first for confidence and avoid false positives.
ReplicationUtils.callEMCRefresh(_helper, storage, true);
Set<String> blockObjectsToAdd = _helper.filterVolumesAlreadyPartOfReplicationGroup(storage, cgPath, blockObjectNames);
if (!blockObjectsToAdd.isEmpty()) {
CIMArgument[] output = new CIMArgument[5];
CIMObjectPath[] members = _cimPath.getVolumePaths(storage, blockObjectsToAdd.toArray(new String[blockObjectsToAdd.size()]));
boolean cgHasGroupRelationship = ControllerUtils.checkCGHasGroupRelationship(storage, consistencyGroup.getId(), _dbClient);
if (!cgHasGroupRelationship) {
CIMArgument[] addMembersInput = _helper.getAddMembersInputArguments(cgPath, members);
_helper.invokeMethod(storage, replicationSvc, SmisConstants.ADD_MEMBERS, addMembersInput, output);
} else {
final CIMObjectPath maskingGroupPath = _cimPath.getMaskingGroupPath(storage, groupName, SmisConstants.MASKING_GROUP_TYPE.SE_DeviceMaskingGroup);
_log.info("Adding volumes {} to device masking group {}", StringUtils.join(blockObjectsToAdd, ", "), maskingGroupPath.toString());
final CIMArgument[] inArgs = _helper.getAddOrRemoveMaskingGroupMembersInputArguments(maskingGroupPath, members, true);
_helper.invokeMethodSynchronously(storage, _cimPath.getControllerConfigSvcPath(storage), SmisConstants.ADD_MEMBERS, inArgs, output, null);
}
} else {
_log.info("Requested volumes {} are already part of the Replication Group {}, hence skipping AddMembers call..", Joiner.on(", ").join(blockObjectNames), groupName);
}
}
// refresh target provider to update its view on target CG
if (isSrdfTarget) {
refreshStorageSystem(storage.getId(), null);
}
}
taskCompleter.ready(_dbClient);
} catch (Exception e) {
_log.error("Problem in adding volumes to Consistency Group {}", consistencyGroupId, e);
// Remove any references to the consistency group
for (URI volume : volumes) {
BlockObject volumeObject = uriToBlockObjectMap.get(volume);
volumeObject.setConsistencyGroup(NullColumnValueGetter.getNullURI());
volumeObject.setReplicationGroupInstance(NullColumnValueGetter.getNullStr());
_dbClient.updateObject(volumeObject);
}
// Remove replication group instance
for (URI replica : replicas) {
BlockObject replicaObject = uriToBlockObjectMap.get(replica);
replicaObject.setReplicationGroupInstance(NullColumnValueGetter.getNullStr());
if (!(replicaObject instanceof Volume && ControllerUtils.isVolumeFullCopy((Volume) replicaObject, _dbClient))) {
replicaObject.setConsistencyGroup(NullColumnValueGetter.getNullURI());
replicaObject.setReplicationGroupInstance(NullColumnValueGetter.getNullStr());
}
_dbClient.updateObject(replicaObject);
}
taskCompleter.error(_dbClient, DeviceControllerException.exceptions.failedToAddMembersToConsistencyGroup(consistencyGroup.getLabel(), consistencyGroup.getCgNameOnStorageSystem(storage.getId()), e.getMessage()));
}
}
use of com.emc.storageos.db.client.model.BlockMirror in project coprhd-controller by CoprHD.
the class SmisBlockCreateCGMirrorJob method updateStatus.
public void updateStatus(JobContext jobContext) throws Exception {
CloseableIterator<CIMInstance> syncVolumeIter = null;
CloseableIterator<CIMObjectPath> repGroupPathIter = null;
DbClient dbClient = jobContext.getDbClient();
BlockMirrorCreateCompleter completer = (BlockMirrorCreateCompleter) getTaskCompleter();
;
JobStatus jobStatus = getJobStatus();
try {
if (jobStatus == JobStatus.IN_PROGRESS) {
return;
}
CIMConnectionFactory cimConnectionFactory = jobContext.getCimConnectionFactory();
WBEMClient client = getWBEMClient(dbClient, cimConnectionFactory);
List<BlockMirror> mirrors = dbClient.queryObject(BlockMirror.class, completer.getIds());
if (jobStatus == JobStatus.SUCCESS || jobStatus == JobStatus.FAILED || jobStatus == JobStatus.FATAL_ERROR) {
updatePools(client, dbClient, mirrors);
}
if (jobStatus == JobStatus.SUCCESS) {
_log.info("Group mirror creation success");
repGroupPathIter = client.associatorNames(getCimJob(), null, SmisConstants.SE_REPLICATION_GROUP, null, null);
CIMObjectPath repGroupPath = repGroupPathIter.next();
StorageSystem storage = dbClient.queryObject(StorageSystem.class, getStorageSystemURI());
String repGroupID = (String) repGroupPath.getKey(SmisConstants.CP_INSTANCE_ID).getValue();
repGroupID = SmisUtils.getTargetGroupName(repGroupID, storage.getUsingSmis80());
CIMInstance syncInst = getSynchronizedInstance(client, repGroupPath);
String syncType = CIMPropertyFactory.getPropertyValue(syncInst, SmisConstants.CP_SYNC_TYPE);
syncVolumeIter = client.associatorInstances(repGroupPath, null, SmisConstants.CIM_STORAGE_VOLUME, null, null, false, _volumeProps);
processCGMirrors(syncVolumeIter, client, dbClient, jobContext.getSmisCommandHelper(), storage, mirrors, repGroupID, syncInst.getObjectPath().toString(), syncType);
} else if (isJobInTerminalFailedState()) {
_log.info("Failed to create group mirrors");
completer.error(dbClient, DeviceControllerException.exceptions.attachVolumeMirrorFailed(getMessage()));
for (BlockMirror mirror : mirrors) {
mirror.setInactive(true);
}
dbClient.persistObject(mirrors);
}
} catch (Exception e) {
setPostProcessingErrorStatus("Encountered an internal error during block create CG mirror job status processing: " + e.getMessage());
_log.error("Caught an exception while trying to updateStatus for SmisBlockCreateCGMirrorJob", e);
} finally {
if (syncVolumeIter != null) {
syncVolumeIter.close();
}
if (repGroupPathIter != null) {
repGroupPathIter.close();
}
super.updateStatus(jobContext);
}
}
use of com.emc.storageos.db.client.model.BlockMirror in project coprhd-controller by CoprHD.
the class SmisBlockDeleteMirrorJob method updateStatus.
@Override
public void updateStatus(JobContext jobContext) throws Exception {
DbClient dbClient = jobContext.getDbClient();
JobStatus jobStatus = getJobStatus();
try {
if (jobStatus == JobStatus.IN_PROGRESS) {
return;
}
BlockMirrorDeleteCompleter completer = (BlockMirrorDeleteCompleter) getTaskCompleter();
BlockMirror mirror = dbClient.queryObject(BlockMirror.class, completer.getMirrorURI());
// If terminal state update storage pool capacity
if (jobStatus == JobStatus.SUCCESS || jobStatus == JobStatus.FAILED || jobStatus == JobStatus.FATAL_ERROR) {
CIMConnectionFactory cimConnectionFactory = jobContext.getCimConnectionFactory();
WBEMClient client = getWBEMClient(dbClient, cimConnectionFactory);
URI poolURI = mirror.getPool();
// Update capacity of storage pools.
SmisUtils.updateStoragePoolCapacity(dbClient, client, poolURI);
}
if (jobStatus == JobStatus.SUCCESS) {
_log.info("Mirror delete success");
Volume volume = dbClient.queryObject(Volume.class, mirror.getSource().getURI());
dbClient.markForDeletion(mirror);
_log.info(String.format("Deleted BlockMirror %s on Volume %s", mirror, volume));
} else if (jobStatus == JobStatus.FATAL_ERROR || jobStatus == JobStatus.FAILED) {
String msg = String.format("Failed to delete mirror %s", mirror.getId());
_log.error(msg);
getTaskCompleter().error(dbClient, DeviceControllerErrors.smis.jobFailed(msg));
}
} catch (Exception e) {
setFatalErrorStatus("Encountered an internal error during block delete mirror job status processing: " + e.getMessage());
_log.error("Caught an exception while trying to updateStatus for SmisBlockDeleteMirrorJob", e);
getTaskCompleter().error(dbClient, DeviceControllerErrors.smis.jobFailed(e.getMessage()));
} finally {
super.updateStatus(jobContext);
}
}
use of com.emc.storageos.db.client.model.BlockMirror in project coprhd-controller by CoprHD.
the class SmisBlockResumeMirrorJob method updateStatus.
@Override
public void updateStatus(JobContext jobContext) throws Exception {
log.info("START updateStatus for resuming {}", getTaskCompleter().getId());
DbClient dbClient = jobContext.getDbClient();
JobStatus jobStatus = getJobStatus();
try {
if (jobStatus == JobStatus.IN_PROGRESS) {
return;
}
BlockMirrorResumeCompleter taskCompleter = (BlockMirrorResumeCompleter) getTaskCompleter();
if (jobStatus == JobStatus.SUCCESS) {
log.info("Mirror resume success");
BlockMirror mirror = dbClient.queryObject(BlockMirror.class, taskCompleter.getMirrorURI());
log.info("Updating sync details for mirror {}", mirror.getId());
WBEMClient client = getWBEMClient(dbClient, jobContext.getCimConnectionFactory());
updateSynchronizationAspects(client, mirror);
dbClient.persistObject(mirror);
getTaskCompleter().ready(dbClient);
} else if (jobStatus == JobStatus.ERROR) {
log.info("Mirror resume failed");
}
} catch (Exception e) {
String errorMsg = "Failed job to resume mirror: " + e.getMessage();
log.error(errorMsg, e);
setPostProcessingErrorStatus(errorMsg);
} finally {
super.updateStatus(jobContext);
log.info("FINISH updateStatus for resuming {}", getTaskCompleter().getId());
}
}
Aggregations