Search in sources :

Example 41 with NamedURI

use of com.emc.storageos.db.client.model.NamedURI in project coprhd-controller by CoprHD.

the class VolumeIngestionUtil method initializeExportGroup.

/**
 * Initialize an Export Group.
 *
 * @param project the Project
 * @param type the ExportGroup type
 * @param vArray the VirtualArray for the ExportGroup
 * @param label the text label for the ExportGroup
 * @param dbClient a reference to the database client
 * @param nameGenerator a name generator
 * @param tenantOrg the TenantOrg to use
 * @return a newly-created ExportGroup
 */
public static ExportGroup initializeExportGroup(Project project, String type, URI vArray, String label, DbClient dbClient, ResourceAndUUIDNameGenerator nameGenerator, TenantOrg tenantOrg) {
    ExportGroup exportGroup = new ExportGroup();
    exportGroup.setLabel(label);
    exportGroup.setType(type);
    exportGroup.setId(URIUtil.createId(ExportGroup.class));
    exportGroup.setProject(new NamedURI(project.getId(), exportGroup.getLabel()));
    exportGroup.setVirtualArray(vArray);
    exportGroup.setTenant(new NamedURI(project.getTenantOrg().getURI(), exportGroup.getLabel()));
    String generatedName = nameGenerator.generate(tenantOrg.getLabel(), exportGroup.getLabel(), exportGroup.getId().toString(), '_', 56);
    exportGroup.setGeneratedName(generatedName);
    return exportGroup;
}
Also used : ExportGroup(com.emc.storageos.db.client.model.ExportGroup) NamedURI(com.emc.storageos.db.client.model.NamedURI)

Example 42 with NamedURI

use of com.emc.storageos.db.client.model.NamedURI in project coprhd-controller by CoprHD.

the class VolumeIngestionUtil method findOrCreateRPBlockConsistencyGroup.

/**
 * Creates a block consistency group for the given protection set, or finds one first
 * if it has already been created in another volume context within the scope of this
 * ingestion request.
 *
 * @param requestContext the current IngestionRequestContext
 * @param unManagedVolume the currently ingesting UnManagedVolume
 * @param pset the ProtectionSet
 * @param dbClient a reference to the database client
 * @return a BlockConsistencyGroup for the volume context and ProtectionSet
 */
public static BlockConsistencyGroup findOrCreateRPBlockConsistencyGroup(IngestionRequestContext requestContext, UnManagedVolume unManagedVolume, ProtectionSet pset, DbClient dbClient) {
    BlockConsistencyGroup cg = null;
    Project project = dbClient.queryObject(Project.class, pset.getProject());
    NamedURI projectNamedUri = new NamedURI(pset.getProject(), project.getLabel());
    // if this is a recover point ingestion context, check for an existing CG in memory
    RecoverPointVolumeIngestionContext rpContext = null;
    if (requestContext instanceof RecoverPointVolumeIngestionContext) {
        rpContext = (RecoverPointVolumeIngestionContext) requestContext;
    } else if (requestContext.getVolumeContext(unManagedVolume.getNativeGuid()) instanceof RecoverPointVolumeIngestionContext) {
        rpContext = (RecoverPointVolumeIngestionContext) requestContext.getVolumeContext(unManagedVolume.getNativeGuid());
    }
    if (rpContext != null) {
        cg = rpContext.findExistingBlockConsistencyGroup(pset.getLabel(), projectNamedUri, project.getTenantOrg());
    }
    // Find the source volume in the protection set so we can set the virtual array in the consistency group
    URI varrayId = null;
    URI storageSystemId = null;
    if (pset.getVolumes() != null) {
        for (String volumeIdStr : pset.getVolumes()) {
            Volume volume = requestContext.findDataObjectByType(Volume.class, URI.create(volumeIdStr), true);
            if (volume != null) {
                if (PersonalityTypes.SOURCE.name().equalsIgnoreCase(volume.getPersonality())) {
                    varrayId = volume.getVirtualArray();
                    if (volume.isVPlexVolume(dbClient)) {
                        storageSystemId = volume.getStorageController();
                    }
                }
            }
        }
    }
    if (cg == null) {
        cg = new BlockConsistencyGroup();
        cg.setId(URIUtil.createId(BlockConsistencyGroup.class));
        cg.setLabel(pset.getLabel());
        cg.setProject(projectNamedUri);
        cg.addConsistencyGroupTypes(Types.RP.name());
        // By default, the array consistency is false. However later when we iterate over volumes in the BCG and we
        // see any replicationGroupInstance information, we'll flip this bit to true. (See decorateRPVolumesCGInfo())
        cg.setArrayConsistency(false);
        cg.setTenant(project.getTenantOrg());
        cg.setVirtualArray(varrayId);
        cg.setStorageController(storageSystemId);
        _logger.info("Created new block consistency group: " + cg.getId().toString());
    }
    cg.addSystemConsistencyGroup(pset.getProtectionSystem().toString(), pset.getLabel());
    return cg;
}
Also used : Project(com.emc.storageos.db.client.model.Project) NamedURI(com.emc.storageos.db.client.model.NamedURI) UnManagedVolume(com.emc.storageos.db.client.model.UnManagedDiscoveredObjects.UnManagedVolume) Volume(com.emc.storageos.db.client.model.Volume) RecoverPointVolumeIngestionContext(com.emc.storageos.api.service.impl.resource.blockingestorchestration.context.impl.RecoverPointVolumeIngestionContext) NamedURI(com.emc.storageos.db.client.model.NamedURI) URI(java.net.URI) BlockConsistencyGroup(com.emc.storageos.db.client.model.BlockConsistencyGroup)

Example 43 with NamedURI

use of com.emc.storageos.db.client.model.NamedURI in project coprhd-controller by CoprHD.

the class BlockDeviceController method restoreVolume.

@Override
public void restoreVolume(URI storage, URI pool, URI volumeURI, URI snapshot, Boolean updateOpStatus, String syncDirection, String opId) throws ControllerException {
    SimpleTaskCompleter completer = new SimpleTaskCompleter(BlockSnapshot.class, snapshot, opId);
    try {
        Workflow workflow = _workflowService.getNewWorkflow(this, RESTORE_VOLUME_WF_NAME, false, opId);
        _log.info("Created new restore workflow with operation id {}", opId);
        Volume volume = _dbClient.queryObject(Volume.class, volumeURI);
        BlockSnapshot blockSnapshot = _dbClient.queryObject(BlockSnapshot.class, snapshot);
        StorageSystem system = _dbClient.queryObject(StorageSystem.class, storage);
        String description = String.format("Restore volume %s from snapshot %s", volumeURI, snapshot);
        String waitFor = null;
        URI srdfSourceStorageSystemURI = null;
        Volume srdfSourceVolume = null;
        Volume srdfTargetVolume = null;
        boolean active = false;
        /**
         * We need to split the SRDF link for R2 snap restore if it is not paused already.
         * Refer OPT#476788
         */
        if (isNonSplitSRDFTargetVolume(volume)) {
            URI srdfSourceVolumeURI = volume.getSrdfParent().getURI();
            srdfSourceVolume = _dbClient.queryObject(Volume.class, srdfSourceVolumeURI);
            srdfTargetVolume = volume;
            srdfSourceStorageSystemURI = srdfSourceVolume.getStorageController();
            if (Mode.ACTIVE.equals(Mode.valueOf(volume.getSrdfCopyMode()))) {
                active = true;
                waitFor = suspendSRDFLinkWorkflowStep(waitFor, srdfSourceStorageSystemURI, srdfSourceVolumeURI, volumeURI, workflow);
            } else {
                // split all members the group
                Workflow.Method splitMethod = srdfDeviceController.splitSRDFGroupLinkMethod(srdfSourceStorageSystemURI, srdfSourceVolumeURI, volumeURI, false);
                Workflow.Method splitRollbackMethod = srdfDeviceController.resumeGroupPairsMethod(srdfSourceStorageSystemURI, srdfSourceVolumeURI, volumeURI);
                waitFor = workflow.createStep(SRDFDeviceController.SPLIT_SRDF_MIRRORS_STEP_GROUP, SRDFDeviceController.SPLIT_SRDF_MIRRORS_STEP_DESC, waitFor, srdfSourceStorageSystemURI, getDeviceType(srdfSourceStorageSystemURI), SRDFDeviceController.class, splitMethod, splitRollbackMethod, null);
            }
        } else if (isNonSplitSRDFSourceVolume(volume)) {
            srdfSourceVolume = volume;
            srdfSourceStorageSystemURI = volume.getStorageController();
            StringSet targets = volume.getSrdfTargets();
            if (null != targets) {
                for (String target : targets) {
                    if (NullColumnValueGetter.isNotNullValue(target)) {
                        srdfTargetVolume = _dbClient.queryObject(Volume.class, URI.create(target));
                        if (null != srdfTargetVolume && Mode.ACTIVE.equals(Mode.valueOf(srdfTargetVolume.getSrdfCopyMode()))) {
                            active = true;
                            waitFor = suspendSRDFLinkWorkflowStep(waitFor, srdfSourceStorageSystemURI, volume.getId(), srdfTargetVolume.getId(), workflow);
                        }
                        break;
                    }
                }
            }
        }
        if (system.checkIfVmax3()) {
            _log.info("Creating workflow for restore VMAX3 snapshot {}", blockSnapshot.getId());
            // To restore the source from a linked target volume for VMAX3 SnapVX, we must
            // do the following:
            // 
            // 1. Terminate any stale restore sessions on the source.
            // 2. Create a temporary snapvx snapshot session of the linked target volume or target group.
            // 3. Link the source volume(s) of the BlockSnapshot(s) to the temporary snapshot session in copy mode.
            // 4. Wait for the data from the session to be copied to the source volume(s)
            // 5. Unlink the source volume(s) from the temporary snapvx snapshot session.
            // 6. Delete the temporary session.
            // 
            // This is essentially restoring by creating a cascaded snapshot session or group
            // snapshot session on the linked target volume associated with the passed block
            // snapshot or associated linked target group in the case of a group operation.
            // Create a workflow step to terminate stale restore sessions.
            waitFor = workflow.createStep(BLOCK_VOLUME_RESTORE_GROUP, String.format("Terminating VMAX restore session from %s to %s", blockSnapshot.getId(), volume.getId()), waitFor, system.getId(), system.getSystemType(), BlockDeviceController.class, terminateRestoreSessionsMethod(system.getId(), volume.getId(), blockSnapshot.getId()), rollbackMethodNullMethod(), null);
            // Get all snapshots if this is a group snapshot.
            String replicationGroupName = null;
            List<BlockSnapshot> allSnapshots = new ArrayList<>();
            String replicationGroupId = blockSnapshot.getReplicationGroupInstance();
            if (!NullColumnValueGetter.isNullValue(replicationGroupId)) {
                allSnapshots.addAll(ControllerUtils.getSnapshotsPartOfReplicationGroup(blockSnapshot, _dbClient));
                int nameStartIndex = replicationGroupId.indexOf("+") + 1;
                replicationGroupName = replicationGroupId.substring(nameStartIndex);
            } else {
                allSnapshots.add(blockSnapshot);
            }
            // Create a temporary BlockSnapshot instance to represent the parent source volumes
            // for each block snapshot. Linking to a session required BlockSnapshot instances so
            // we need to create some to represent the source volume(s).
            StringSet linkedTargets = new StringSet();
            List<BlockSnapshot> sourceSnapshots = new ArrayList<>();
            List<URI> sourceSnapshotURIs = new ArrayList<>();
            URI cgURI = blockSnapshot.getConsistencyGroup();
            for (BlockSnapshot aSnapshot : allSnapshots) {
                BlockObject aSourceObj = BlockObject.fetch(_dbClient, aSnapshot.getParent().getURI());
                BlockSnapshot sourceSnapshot = new BlockSnapshot();
                URI sourceSnapshotURI = URIUtil.createId(BlockSnapshot.class);
                sourceSnapshot.setId(sourceSnapshotURI);
                sourceSnapshot.setNativeId(aSourceObj.getNativeId());
                sourceSnapshot.setParent(new NamedURI(aSnapshot.getId(), aSnapshot.getLabel()));
                sourceSnapshot.setSourceNativeId(aSnapshot.getNativeId());
                sourceSnapshot.setStorageController(storage);
                sourceSnapshot.setSystemType(system.getSystemType());
                if (!NullColumnValueGetter.isNullURI(cgURI)) {
                    sourceSnapshot.setConsistencyGroup(cgURI);
                }
                sourceSnapshot.addInternalFlags(Flag.INTERNAL_OBJECT);
                sourceSnapshots.add(sourceSnapshot);
                sourceSnapshotURIs.add(sourceSnapshotURI);
                linkedTargets.add(sourceSnapshotURI.toString());
            }
            _dbClient.createObject(sourceSnapshots);
            // Create a BlockSnapshotSession instance to represent the temporary snapshot session.
            BlockSnapshotSession snapSession = new BlockSnapshotSession();
            URI snapSessionURI = URIUtil.createId(BlockSnapshotSession.class);
            snapSession.setId(snapSessionURI);
            snapSession.setLabel(blockSnapshot.getLabel() + System.currentTimeMillis());
            snapSession.setSessionLabel(snapSession.getLabel());
            snapSession.setProject(blockSnapshot.getProject());
            snapSession.setStorageController(storage);
            snapSession.addInternalFlags(Flag.INTERNAL_OBJECT);
            if (!NullColumnValueGetter.isNullURI(cgURI) && NullColumnValueGetter.isNotNullValue(replicationGroupName)) {
                snapSession.setConsistencyGroup(cgURI);
                snapSession.setReplicationGroupInstance(replicationGroupName);
                snapSession.setSessionSetName(replicationGroupName);
            } else {
                snapSession.setParent(new NamedURI(blockSnapshot.getId(), blockSnapshot.getLabel()));
            }
            snapSession.setLinkedTargets(linkedTargets);
            _dbClient.createObject(snapSession);
            // Now create a workflow step that will create the snapshot session.
            // This will create a group session in the case of a group operation.
            waitFor = workflow.createStep(CREATE_SNAPSHOT_SESSION_STEP_GROUP, String.format("Create snapshot session %s for snapshot target volume %s", snapSessionURI, snapshot), waitFor, storage, getDeviceType(storage), BlockDeviceController.class, createBlockSnapshotSessionMethod(storage, snapSessionURI, replicationGroupName), deleteBlockSnapshotSessionMethod(storage, snapSessionURI, replicationGroupName, Boolean.TRUE), null);
            // Create a workflow step to link the source volume for the passed snapshot
            // to the snapshot session create by the previous step. We link the source
            // volume in copy mode so that that the point-in-time copy of the snapshot
            // target volume represented by the snapshot session is copied to the source
            // volume. This is essentially the restore step so that the source will now
            // reflect the data on the snapshot target volume. This step will not complete
            // until the data is copied and the link has achieved the copied state. If this
            // is group operation the source target group will be linked to the created
            // group session.
            Workflow.Method linkMethod;
            if (!NullColumnValueGetter.isNullURI(cgURI) && NullColumnValueGetter.isNotNullValue(replicationGroupName)) {
                linkMethod = linkBlockSnapshotSessionTargetGroupMethod(storage, snapSessionURI, sourceSnapshotURIs, BlockSnapshotSession.CopyMode.copy.name(), Boolean.TRUE);
            } else {
                linkMethod = linkBlockSnapshotSessionTargetMethod(storage, snapSessionURI, sourceSnapshotURIs.get(0), BlockSnapshotSession.CopyMode.copy.name(), Boolean.TRUE);
            }
            waitFor = workflow.createStep(LINK_SNAPSHOT_SESSION_TARGET_STEP_GROUP, String.format("Link source volume %s to snapshot session for snapshot target volume %s", volume, snapshot), waitFor, storage, getDeviceType(storage), BlockDeviceController.class, linkMethod, unlinkBlockSnapshotSessionTargetMethod(storage, snapSessionURI, sourceSnapshotURIs.get(0), Boolean.FALSE), null);
            // Once the data is fully copied to the source, we can unlink the source from the session.
            // Again, for a group operation, this will unlink the source group from the group session.
            waitFor = workflow.createStep(UNLINK_SNAPSHOT_SESSION_TARGET_STEP_GROUP, String.format("Unlink source volume %s from snapshot session for snapshot target volume %s", volumeURI, snapshot), waitFor, storage, getDeviceType(storage), BlockDeviceController.class, unlinkBlockSnapshotSessionTargetMethod(storage, snapSessionURI, sourceSnapshotURIs.get(0), Boolean.FALSE), rollbackMethodNullMethod(), null);
            // Finally create a step to delete the snapshot session we created on the snapshot
            // target volume.
            waitFor = workflow.createStep(DELETE_SNAPSHOT_SESSION_STEP_GROUP, String.format("Delete snapshot session %s for snapshot target volume %s", snapSessionURI, snapshot), waitFor, storage, getDeviceType(storage), BlockDeviceController.class, deleteBlockSnapshotSessionMethod(storage, snapSessionURI, replicationGroupName, Boolean.TRUE), rollbackMethodNullMethod(), null);
            /*
                 * If Active mode then create a step to resume srdf group or restore R2 To R1 or do nothing.
                 * If syncdirection is not specified means its null then after R1 snapshot restore, resume.
                 * If syncdirection is not specified means its null then after R2 snapshot restore, restore R2 to R1.
                 * If syncdirection is SOURCE_TO_TARGET then after R1 or R2 snapshot restore, resume.
                 * If syncdirection is TARGET_TO_SOURCE then after R1 or R2 snapshot restore, restore R2 to R1.
                 * If syncdirection is NONE then do nothing, RDF group will stay in suspend state.
                 */
            if (active) {
                if (null == syncDirection) {
                    if (null != srdfSourceVolume && volumeURI.equals(srdfSourceVolume.getId())) {
                        resumeSRDFLinkWorkflowStep(waitFor, srdfSourceStorageSystemURI, srdfSourceVolume.getId(), srdfTargetVolume.getId(), workflow);
                    } else if (null != srdfTargetVolume && volumeURI.equals(srdfTargetVolume.getId())) {
                        restoreWorkflowStep(waitFor, srdfTargetVolume.getStorageController(), srdfSourceVolume.getId(), srdfTargetVolume.getId(), workflow);
                    }
                } else if (null != syncDirection) {
                    if (SRDFUtils.SyncDirection.SOURCE_TO_TARGET.toString().equals(syncDirection)) {
                        resumeSRDFLinkWorkflowStep(waitFor, srdfSourceStorageSystemURI, srdfSourceVolume.getId(), srdfTargetVolume.getId(), workflow);
                    } else if (SRDFUtils.SyncDirection.TARGET_TO_SOURCE.toString().equals(syncDirection)) {
                        restoreWorkflowStep(waitFor, srdfTargetVolume.getStorageController(), srdfSourceVolume.getId(), srdfTargetVolume.getId(), workflow);
                    } else if (SRDFUtils.SyncDirection.NONE.toString().equals(syncDirection)) {
                        _log.info("Sync direction is specified as {} hence no action will be done after retsore snapshot which" + " means the RDF group for volume {} will be in a suspended state.", syncDirection, volume.getLabel());
                    }
                }
            }
        } else {
            waitFor = workflow.createStep(BLOCK_VOLUME_RESTORE_GROUP, description, waitFor, storage, getDeviceType(storage), BlockDeviceController.class, restoreVolumeMethod(storage, pool, volumeURI, snapshot, updateOpStatus), rollbackMethodNullMethod(), null);
            // Skip the step for VMAX3, as restore operation may still be in progress (OPT#476325)
            // Regardless, termination of restore session should be call before restore
            // Note this is not needed for VNX
            addPostRestoreVolumeSteps(workflow, system, volume, blockSnapshot, waitFor);
        }
        _log.info("Executing workflow {}", BLOCK_VOLUME_RESTORE_GROUP);
        String msg = String.format("Restore of volume %s from %s completed successfully", volumeURI, snapshot);
        workflow.executePlan(completer, msg);
    } catch (Exception e) {
        String msg = String.format("Could not restore volume %s from snapshot %s", volumeURI, snapshot);
        _log.error(msg, e);
        ServiceError serviceError = DeviceControllerException.errors.jobFailed(e);
        completer.error(_dbClient, serviceError);
    }
}
Also used : ServiceError(com.emc.storageos.svcs.errorhandling.model.ServiceError) BlockSnapshotSession(com.emc.storageos.db.client.model.BlockSnapshotSession) NamedURI(com.emc.storageos.db.client.model.NamedURI) BlockSnapshot(com.emc.storageos.db.client.model.BlockSnapshot) ArrayList(java.util.ArrayList) Workflow(com.emc.storageos.workflow.Workflow) NamedURI(com.emc.storageos.db.client.model.NamedURI) FCTN_MIRROR_TO_URI(com.emc.storageos.db.client.util.CommonTransformerFunctions.FCTN_MIRROR_TO_URI) URI(java.net.URI) PrefixConstraint(com.emc.storageos.db.client.constraint.PrefixConstraint) ContainmentConstraint(com.emc.storageos.db.client.constraint.ContainmentConstraint) InternalException(com.emc.storageos.svcs.errorhandling.resources.InternalException) BaseCollectionException(com.emc.storageos.plugins.BaseCollectionException) ControllerException(com.emc.storageos.volumecontroller.ControllerException) WorkflowException(com.emc.storageos.workflow.WorkflowException) DatabaseException(com.emc.storageos.db.exceptions.DatabaseException) DeviceControllerException(com.emc.storageos.exceptions.DeviceControllerException) DataBindingException(javax.xml.bind.DataBindingException) Volume(com.emc.storageos.db.client.model.Volume) SRDFDeviceController(com.emc.storageos.srdfcontroller.SRDFDeviceController) StringSet(com.emc.storageos.db.client.model.StringSet) SimpleTaskCompleter(com.emc.storageos.volumecontroller.impl.block.taskcompleter.SimpleTaskCompleter) BlockObject(com.emc.storageos.db.client.model.BlockObject) StorageSystem(com.emc.storageos.db.client.model.StorageSystem)

Example 44 with NamedURI

use of com.emc.storageos.db.client.model.NamedURI in project coprhd-controller by CoprHD.

the class HDSMirrorOperations method detachSingleVolumeMirror.

/**
 * 1. Delete ShadowImage Pair
 * 2. Delete DummyLunPath from secondary volume
 */
@Override
public void detachSingleVolumeMirror(StorageSystem storage, URI mirror, TaskCompleter taskCompleter) throws DeviceControllerException {
    NamedURI sourceVolumeURI = null;
    try {
        BlockMirror mirrorObj = dbClient.queryObject(BlockMirror.class, mirror);
        // TODO needs to sync pair and wait for synchronization here
        Volume source = dbClient.queryObject(Volume.class, mirrorObj.getSource());
        sourceVolumeURI = mirrorObj.getSource();
        boolean status = hdsProtectionOperations.modifyShadowImagePair(storage, source.getNativeId(), mirrorObj.getNativeId(), HDSApiProtectionManager.ShadowImageOperationType.split);
        if (status) {
            String taskId = UUID.randomUUID().toString();
            TaskCompleter completer = new SimpleTaskCompleter(BlockMirror.class, mirror, taskId);
            HDSJob syncjob = new HDSReplicationSyncJob(storage.getId(), source.getNativeId(), mirrorObj.getNativeId(), ReplicationStatus.SPLIT, completer);
            hdsCommandHelper.waitForAsyncHDSJob(syncjob);
        } else {
            log.info("Replication info is not available on pair management server");
        }
        hdsProtectionOperations.deleteShadowImagePair(storage, source, mirrorObj);
        hdsProtectionOperations.removeDummyLunPath(storage, mirror);
        taskCompleter.ready(dbClient);
    } catch (Exception e) {
        String errorMsg = String.format(DETACH_ERROR_MSG_FORMAT, mirror, sourceVolumeURI != null ? sourceVolumeURI.toString() : HDSConstants.SPACE_STR);
        log.error(errorMsg, e);
        ServiceError serviceError = DeviceControllerErrors.hds.methodFailed("detachSingleVolumeMirror", e.getMessage());
        taskCompleter.error(dbClient, serviceError);
    }
}
Also used : HDSReplicationSyncJob(com.emc.storageos.volumecontroller.impl.hds.prov.job.HDSReplicationSyncJob) ServiceError(com.emc.storageos.svcs.errorhandling.model.ServiceError) BlockMirror(com.emc.storageos.db.client.model.BlockMirror) HDSJob(com.emc.storageos.volumecontroller.impl.hds.prov.job.HDSJob) NamedURI(com.emc.storageos.db.client.model.NamedURI) Volume(com.emc.storageos.db.client.model.Volume) SimpleTaskCompleter(com.emc.storageos.volumecontroller.impl.block.taskcompleter.SimpleTaskCompleter) SimpleTaskCompleter(com.emc.storageos.volumecontroller.impl.block.taskcompleter.SimpleTaskCompleter) TaskCompleter(com.emc.storageos.volumecontroller.TaskCompleter) DeviceControllerException(com.emc.storageos.exceptions.DeviceControllerException) HDSException(com.emc.storageos.hds.HDSException)

Example 45 with NamedURI

use of com.emc.storageos.db.client.model.NamedURI in project coprhd-controller by CoprHD.

the class CephCloneOperations method createSingleClone.

@Override
public void createSingleClone(StorageSystem storageSystem, URI source, URI cloneVolume, Boolean createInactive, TaskCompleter taskCompleter) {
    _log.info("START createSingleClone operation");
    try (CephClient cephClient = getClient(storageSystem)) {
        Volume cloneObject = _dbClient.queryObject(Volume.class, cloneVolume);
        BlockObject sourceObject = BlockObject.fetch(_dbClient, source);
        BlockSnapshot sourceSnapshot = null;
        Volume parentVolume = null;
        if (sourceObject instanceof BlockSnapshot) {
            // Use source snapshot as clone source
            sourceSnapshot = (BlockSnapshot) sourceObject;
            parentVolume = _dbClient.queryObject(Volume.class, sourceSnapshot.getParent());
        } else if (sourceObject instanceof Volume) {
            // Use interim snapshot as clone source, since Ceph can clone snapshots only
            // http://docs.ceph.com/docs/master/rbd/rbd-snapshot/#getting-started-with-layering
            parentVolume = (Volume) sourceObject;
            sourceSnapshot = prepareInternalSnapshotForVolume(parentVolume);
        } else {
            String msg = String.format("Unsupported block object type URI %s", source);
            ServiceCoded code = DeviceControllerErrors.ceph.operationFailed("createSingleClone", msg);
            taskCompleter.error(_dbClient, code);
            return;
        }
        StoragePool pool = _dbClient.queryObject(StoragePool.class, parentVolume.getPool());
        String poolId = pool.getPoolName();
        String parentVolumeId = parentVolume.getNativeId();
        String snapshotId = sourceSnapshot.getNativeId();
        String cloneId = null;
        try {
            if (snapshotId == null || snapshotId.isEmpty()) {
                // Create Ceph snapshot of volume requested to clone
                snapshotId = CephUtils.createNativeId(sourceSnapshot);
                cephClient.createSnap(poolId, parentVolumeId, snapshotId);
                sourceSnapshot.setNativeId(snapshotId);
                sourceSnapshot.setDeviceLabel(snapshotId);
                sourceSnapshot.setIsSyncActive(true);
                sourceSnapshot.setParent(new NamedURI(parentVolume.getId(), parentVolume.getLabel()));
                _dbClient.updateObject(sourceSnapshot);
                _log.info("Interim shapshot {} created for clone {}", sourceSnapshot.getId(), cloneObject.getId());
            }
            // Ceph requires cloning snapshot to be protected (from deleting)
            if (!cephClient.snapIsProtected(poolId, parentVolumeId, snapshotId)) {
                cephClient.protectSnap(poolId, parentVolumeId, snapshotId);
            }
            // Do cloning
            String cloneVolumeId = CephUtils.createNativeId(cloneObject);
            cephClient.cloneSnap(poolId, parentVolumeId, snapshotId, cloneVolumeId);
            cloneId = cloneVolumeId;
            // Update clone object
            cloneObject.setDeviceLabel(cloneId);
            cloneObject.setNativeId(cloneId);
            cloneObject.setNativeGuid(NativeGUIDGenerator.generateNativeGuid(_dbClient, cloneObject));
            cloneObject.setProvisionedCapacity(parentVolume.getProvisionedCapacity());
            cloneObject.setAllocatedCapacity(parentVolume.getAllocatedCapacity());
            cloneObject.setAssociatedSourceVolume(sourceSnapshot.getId());
            _dbClient.updateObject(cloneObject);
            // Finish task
            taskCompleter.ready(_dbClient);
        } catch (Exception e) {
            // Clean up created objects
            cleanUpCloneObjects(cephClient, poolId, cloneId, snapshotId, parentVolumeId, sourceSnapshot);
            throw e;
        }
    } catch (Exception e) {
        BlockObject obj = BlockObject.fetch(_dbClient, cloneVolume);
        if (obj != null) {
            obj.setInactive(true);
            _dbClient.updateObject(obj);
        }
        _log.error("Encountered an exception", e);
        ServiceCoded code = DeviceControllerErrors.ceph.operationFailed("createSingleClone", e.getMessage());
        taskCompleter.error(_dbClient, code);
    }
}
Also used : StoragePool(com.emc.storageos.db.client.model.StoragePool) Volume(com.emc.storageos.db.client.model.Volume) NamedURI(com.emc.storageos.db.client.model.NamedURI) ServiceCoded(com.emc.storageos.svcs.errorhandling.model.ServiceCoded) BlockSnapshot(com.emc.storageos.db.client.model.BlockSnapshot) CephClient(com.emc.storageos.ceph.CephClient) BlockObject(com.emc.storageos.db.client.model.BlockObject)

Aggregations

NamedURI (com.emc.storageos.db.client.model.NamedURI)196 URI (java.net.URI)98 Volume (com.emc.storageos.db.client.model.Volume)74 StringSet (com.emc.storageos.db.client.model.StringSet)65 Project (com.emc.storageos.db.client.model.Project)54 ArrayList (java.util.ArrayList)46 TenantOrg (com.emc.storageos.db.client.model.TenantOrg)43 StorageSystem (com.emc.storageos.db.client.model.StorageSystem)42 BlockSnapshot (com.emc.storageos.db.client.model.BlockSnapshot)36 Test (org.junit.Test)32 StoragePool (com.emc.storageos.db.client.model.StoragePool)31 VirtualPool (com.emc.storageos.db.client.model.VirtualPool)31 VirtualArray (com.emc.storageos.db.client.model.VirtualArray)27 BlockConsistencyGroup (com.emc.storageos.db.client.model.BlockConsistencyGroup)26 StringMap (com.emc.storageos.db.client.model.StringMap)26 List (java.util.List)23 OpStatusMap (com.emc.storageos.db.client.model.OpStatusMap)20 StringSetMap (com.emc.storageos.db.client.model.StringSetMap)20 VirtualPoolCapabilityValuesWrapper (com.emc.storageos.volumecontroller.impl.utils.VirtualPoolCapabilityValuesWrapper)18 FileShare (com.emc.storageos.db.client.model.FileShare)17