Search in sources :

Example 21 with ProtectionSystem

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

the class RPDeviceController method cgCreateStep.

/**
 * Workflow step method for creating/updating a consistency group.
 *
 * @param rpSystemId
 *            RP system Id
 * @param recommendation
 *            parameters needed to create the CG
 * @param token
 *            the task
 * @return
 * @throws InternalException
 */
public boolean cgCreateStep(URI rpSystemId, List<VolumeDescriptor> volumeDescriptors, String token) throws InternalException {
    RecoverPointClient rp;
    CGRequestParams cgParams = null;
    boolean metropoint = false;
    boolean lockException = false;
    try {
        // Get only the RP volumes from the descriptors.
        List<VolumeDescriptor> sourceVolumeDescriptors = VolumeDescriptor.filterByType(volumeDescriptors, new VolumeDescriptor.Type[] { VolumeDescriptor.Type.RP_SOURCE, VolumeDescriptor.Type.RP_EXISTING_SOURCE, VolumeDescriptor.Type.RP_VPLEX_VIRT_SOURCE }, new VolumeDescriptor.Type[] {});
        WorkflowStepCompleter.stepExecuting(token);
        ProtectionSystem rpSystem = _dbClient.queryObject(ProtectionSystem.class, rpSystemId);
        URI cgId = volumeDescriptors.iterator().next().getCapabilitiesValues().getBlockConsistencyGroup();
        boolean attachAsClean = true;
        for (VolumeDescriptor sourceVolumedescriptor : sourceVolumeDescriptors) {
            Volume sourceVolume = _dbClient.queryObject(Volume.class, sourceVolumedescriptor.getVolumeURI());
            metropoint = RPHelper.isMetroPointVolume(_dbClient, sourceVolume);
            // if this is a change vpool, attachAsClean should be false so that source and target are synchronized
            if (VolumeDescriptor.Type.RP_EXISTING_SOURCE.equals(sourceVolumedescriptor.getType())) {
                attachAsClean = false;
            }
        }
        // Build the CG Request params
        cgParams = getCGRequestParams(volumeDescriptors, rpSystem);
        updateCGParams(cgParams);
        // Validate the source/target volumes before creating a CG.
        validateCGVolumes(volumeDescriptors);
        rp = RPHelper.getRecoverPointClient(rpSystem);
        // Scan the rp sites for volume visibility
        rp.waitForVolumesToBeVisible(cgParams);
        // Before acquiring a lock on the CG we need to ensure that the
        // CG is created. If it hasn't, then the first CGRequestParams
        // to be allowed to pass through needs to have the journals
        // defined.
        // 
        // NOTE: The CG may not yet be created on the RP protection system and
        // that's OK since this might be the first request going in.
        waitForCGToBeCreated(cgId, cgParams);
        // lock around create and delete operations on the same CG
        List<String> lockKeys = new ArrayList<String>();
        lockKeys.add(ControllerLockingUtil.getConsistencyGroupStorageKey(_dbClient, cgId, rpSystem.getId()));
        boolean lockAcquired = _workflowService.acquireWorkflowStepLocks(token, lockKeys, LockTimeoutValue.get(LockType.RP_CG));
        if (!lockAcquired) {
            lockException = true;
            throw DeviceControllerException.exceptions.failedToAcquireLock(lockKeys.toString(), String.format("Create or add volumes to RP consistency group id: %s", cgId.toString()));
        }
        RecoverPointCGResponse response = null;
        // The CG already exists if it contains volumes and is of type RP
        _log.info("Submitting RP Request: " + cgParams);
        BlockConsistencyGroup cg = _dbClient.queryObject(BlockConsistencyGroup.class, cgId);
        // Check to see if the CG has been created in ViPR and on the RP protection system
        boolean cgAlreadyExists = rpCGExists(cg, rp, cgParams.getCgName(), rpSystem.getId());
        if (cgAlreadyExists) {
            // cg exists in both the ViPR db and on the RP system
            _log.info(String.format("RP CG [%s] already exists, adding replication set(s) to it...", cgParams.getCgName()));
            response = rp.addReplicationSetsToCG(cgParams, metropoint, attachAsClean);
        } else {
            _log.info(String.format("RP CG [%s] does not already exist, creating it now and adding replication set(s) to it...", cgParams.getCgName()));
            response = rp.createCG(cgParams, metropoint, attachAsClean);
            // "Turn-on" the consistency group
            cg = _dbClient.queryObject(BlockConsistencyGroup.class, cgParams.getCgUri());
            cg.addSystemConsistencyGroup(rpSystemId.toString(), cgParams.getCgName());
            cg.addConsistencyGroupTypes(Types.RP.name());
        }
        // At this point, always clear the journal provisioning lock on the
        // CG for any concurrent orders that may come in.
        cg.setJournalProvisioningLock(0L);
        _dbClient.updateObject(cg);
        setVolumeConsistencyGroup(volumeDescriptors, cgParams.getCgUri());
        // If this was a vpool Update, now is a good time to update the vpool and Volume information
        if (VolumeDescriptor.getVirtualPoolChangeVolume(volumeDescriptors) != null) {
            Volume volume = _dbClient.queryObject(Volume.class, VolumeDescriptor.getVirtualPoolChangeVolume(volumeDescriptors));
            URI newVpoolURI = getVirtualPoolChangeNewVirtualPool(volumeDescriptors);
            volume.setVirtualPool(newVpoolURI);
            volume.setPersonality(Volume.PersonalityTypes.SOURCE.toString());
            volume.setAccessState(Volume.VolumeAccessState.READWRITE.name());
            volume.setLinkStatus(Volume.LinkStatus.IN_SYNC.name());
            volume.setProtectionController(rpSystemId);
            _dbClient.updateObject(volume);
            // We might need to update the vpools of the backing volumes if this is an RP+VPLEX
            // or MetroPoint change vpool.
            VPlexUtil.updateVPlexBackingVolumeVpools(volume, newVpoolURI, _dbClient);
            // Record Audit operation. (virtualpool change only)
            AuditBlockUtil.auditBlock(_dbClient, OperationTypeEnum.CHANGE_VOLUME_VPOOL, true, AuditLogManager.AUDITOP_END, token);
        }
        // Create the ProtectionSet to contain the CG UID (which is truly unique to the protection system)
        if (response.getCgId() != null) {
            List<ProtectionSet> protectionSets = CustomQueryUtility.queryActiveResourcesByConstraint(_dbClient, ProtectionSet.class, AlternateIdConstraint.Factory.getConstraint(ProtectionSet.class, "protectionId", response.getCgId().toString()));
            ProtectionSet protectionSet = null;
            if (protectionSets.isEmpty()) {
                // A protection set corresponding to the CG does not exist so we need to create one
                protectionSet = createProtectionSet(rpSystem, cgParams, response.getCgId());
            } else {
                // Update the existing protection set. We will only have 1 protection set
                // get the first one.
                protectionSet = protectionSets.get(0);
                protectionSet = updateProtectionSet(protectionSet, cgParams);
            }
            _dbClient.updateObject(protectionSet);
        }
        // Set the CG last created time to now.
        rpSystem.setCgLastCreatedTime(Calendar.getInstance());
        _dbClient.updateObject(rpSystem);
        // Update the workflow state.
        WorkflowStepCompleter.stepSucceded(token);
        // collect and update the protection system statistics to account for
        // the newly created CG.
        _log.info("Collecting RP statistics post CG create.");
        collectRPStatistics(rpSystem);
    } catch (Exception e) {
        if (lockException) {
            List<URI> volUris = VolumeDescriptor.getVolumeURIs(volumeDescriptors);
            ServiceError serviceError = DeviceControllerException.errors.createVolumesAborted(volUris.toString(), e);
            doFailCgCreateStep(volumeDescriptors, cgParams, rpSystemId, token);
            stepFailed(token, serviceError, "cgCreateStep");
        } else {
            doFailCgCreateStep(volumeDescriptors, cgParams, rpSystemId, token);
            stepFailed(token, e, "cgCreateStep");
        }
        return false;
    }
    return true;
}
Also used : RecoverPointCGResponse(com.emc.storageos.recoverpoint.responses.RecoverPointCGResponse) ServiceError(com.emc.storageos.svcs.errorhandling.model.ServiceError) VolumeDescriptor(com.emc.storageos.blockorchestrationcontroller.VolumeDescriptor) ArrayList(java.util.ArrayList) ProtectionSet(com.emc.storageos.db.client.model.ProtectionSet) ProtectionSystem(com.emc.storageos.db.client.model.ProtectionSystem) NamedURI(com.emc.storageos.db.client.model.NamedURI) URI(java.net.URI) InternalException(com.emc.storageos.svcs.errorhandling.resources.InternalException) InternalServerErrorException(com.emc.storageos.svcs.errorhandling.resources.InternalServerErrorException) ControllerException(com.emc.storageos.volumecontroller.ControllerException) LockRetryException(com.emc.storageos.locking.LockRetryException) FunctionalAPIActionFailedException_Exception(com.emc.fapiclient.ws.FunctionalAPIActionFailedException_Exception) URISyntaxException(java.net.URISyntaxException) WorkflowException(com.emc.storageos.workflow.WorkflowException) DatabaseException(com.emc.storageos.db.exceptions.DatabaseException) DeviceControllerException(com.emc.storageos.exceptions.DeviceControllerException) FunctionalAPIInternalError_Exception(com.emc.fapiclient.ws.FunctionalAPIInternalError_Exception) CoordinatorException(com.emc.storageos.coordinator.exceptions.CoordinatorException) RecoverPointException(com.emc.storageos.recoverpoint.exceptions.RecoverPointException) BlockConsistencyGroup(com.emc.storageos.db.client.model.BlockConsistencyGroup) Volume(com.emc.storageos.db.client.model.Volume) RecoverPointClient(com.emc.storageos.recoverpoint.impl.RecoverPointClient) CGRequestParams(com.emc.storageos.recoverpoint.requests.CGRequestParams) ApplicationAddVolumeList(com.emc.storageos.volumecontroller.ApplicationAddVolumeList) ArrayList(java.util.ArrayList) URIQueryResultList(com.emc.storageos.db.client.constraint.URIQueryResultList) List(java.util.List)

Example 22 with ProtectionSystem

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

the class ConnectivityUtil method getProtectionSystemsForStoragePool.

/**
 * Gets a list of the RP Protection systems for the passed pool.
 *
 * @param dbClient Reference to a DB client
 * @param storagePool Reference to a storage pool
 * @param varrayId Optional, filter by varray
 * @param isRPVPlex Optional, specifies whether or not this is an RP+VPLEX/MetroPoint request
 *
 * @return A list of the RP protection systems.
 */
public static Set<ProtectionSystem> getProtectionSystemsForStoragePool(DbClient dbClient, StoragePool storagePool, URI varrayId, boolean isRPVPlex) {
    Set<ProtectionSystem> rpSystems = new HashSet<ProtectionSystem>();
    Set<ProtectionSystem> rpSystemsWithIsolatedVarrayEntry = new HashSet<ProtectionSystem>();
    List<String> isolatedRPSites = new ArrayList<String>();
    List<String> storageSystems = new ArrayList<String>();
    _log.info(String.format("Find Protection Systems using the Storage System of Storage pool [%s]", storagePool.getLabel()));
    // the VPLEX.
    if (isRPVPlex) {
        _log.info(String.format("RP+VPlex/MetroPoint - only consider Protection Systems associated to the VPLEX."));
        // Get the VPLEXs associated with the Storage Pool
        List<String> vplexSystemsForPool = VPlexHighAvailabilityMatcher.getVPlexStorageSystemsForStorageSystem(dbClient, storagePool.getStorageDevice(), null);
        // Loop through all the VPLEXs
        for (String vplexId : vplexSystemsForPool) {
            if (varrayId != null) {
                // Find the VPLEX(s) that are associated to this varray
                List<URI> vplexVarrays = ConnectivityUtil.getVPlexSystemVarrays(dbClient, URI.create(vplexId));
                if (vplexVarrays.contains(varrayId)) {
                    _log.info(String.format("Candidate VPLEX Storage System [%s]", vplexId));
                    storageSystems.add(vplexId);
                }
            } else {
                _log.info(String.format("Candidate VPLEX Storage System [%s]", vplexId));
                storageSystems.add(vplexId);
            }
        }
    } else {
        _log.info(String.format("Candidate Storage System [%s]", storagePool.getStorageDevice().toASCIIString()));
        storageSystems.add(storagePool.getStorageDevice().toASCIIString());
    }
    // Find all the Protection Systems for these Storage Systems
    for (String storageSystemId : storageSystems) {
        Set<URI> rpSystemURIs = ConnectivityUtil.getProtectionSystemsAssociatedWithArray(dbClient, URI.create(storageSystemId));
        for (URI uri : rpSystemURIs) {
            ProtectionSystem ps = dbClient.queryObject(ProtectionSystem.class, uri);
            // Make sure the ProtectionSystem is active
            if (ps != null && !ps.getInactive()) {
                // We could be isolating the varray in question to specific RPA clusters/sites.
                // If there is an entry for this varray in the siteAssignedVirtualArrays field
                // we need to honour that isolation and only return Protection Systems
                // with an entry for that varray.
                boolean varrayHasBeenIsolated = false;
                if (varrayId != null) {
                    if (ps.getSiteAssignedVirtualArrays() != null && !ps.getSiteAssignedVirtualArrays().isEmpty()) {
                        // Loop over all entries to see if this Protection System has an entry for this varray to be isolated
                        for (Map.Entry<String, AbstractChangeTrackingSet<String>> entry : ps.getSiteAssignedVirtualArrays().entrySet()) {
                            // Check to see if this entry contains the varray
                            if (entry.getValue().contains(varrayId.toString())) {
                                // This varray has been isolated to a RP cluster/site
                                varrayHasBeenIsolated = true;
                                isolatedRPSites.add(entry.getKey());
                                break;
                            }
                        }
                    }
                }
                _log.info(String.format("Found Protection System [%s]", ps.getLabel()));
                if (varrayHasBeenIsolated) {
                    rpSystemsWithIsolatedVarrayEntry.add(ps);
                } else {
                    rpSystems.add(ps);
                }
            } else {
                _log.info(String.format("Excluding ProtectionSystem %s because it is inactive or invalid.", uri));
            }
        }
    }
    // connectivity.
    if (!rpSystemsWithIsolatedVarrayEntry.isEmpty()) {
        // Only use RP Systems that have an entry for this varray,
        // we will ignore the others.
        rpSystems = rpSystemsWithIsolatedVarrayEntry;
        StringBuffer logMsg = new StringBuffer();
        logMsg.append(String.format("Varray [%s] has been isolated to these RP Sites: %s %n", varrayId.toString(), Joiner.on(',').join(isolatedRPSites)));
        logMsg.append("Therefore only these Protection Systems can be used: ");
        for (ProtectionSystem ps : rpSystems) {
            logMsg.append(ps.getLabel() + " ");
        }
        _log.info(logMsg.toString());
    }
    return rpSystems;
}
Also used : ArrayList(java.util.ArrayList) ProtectionSystem(com.emc.storageos.db.client.model.ProtectionSystem) URI(java.net.URI) HashMap(java.util.HashMap) Map(java.util.Map) HashSet(java.util.HashSet) AbstractChangeTrackingSet(com.emc.storageos.db.client.model.AbstractChangeTrackingSet)

Example 23 with ProtectionSystem

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

the class ConnectivityUtil method updateRpSystemsConnectivity.

/**
 * Refreshes the connected virtual arrays for the Recover Point (RP) systems that have sites for the storage systems.
 * This function:
 * <ol>
 * <li>Finds all the RP systems that have sites in one or more of the storage systems</li>
 * <li>for each RP system, find all the virtual arrays for all their connected storage systems' pools.</li>
 * </ol>
 *
 * @param storageSystemUris the storage systems that have some change in their varray associations
 * @param dbClient an instance of {@link DbClient}
 */
public static void updateRpSystemsConnectivity(Collection<URI> storageSystemUris, DbClient dbClient) {
    if (storageSystemUris.isEmpty()) {
        return;
    }
    List<URI> connectedRPSystems = getConnectedRPSystems(storageSystemUris, dbClient);
    List<ProtectionSystem> rpSystems = dbClient.queryObject(ProtectionSystem.class, connectedRPSystems);
    for (ProtectionSystem rpSystem : rpSystems) {
        updateRpSystemConnectivity(rpSystem, dbClient);
    }
}
Also used : URI(java.net.URI) ProtectionSystem(com.emc.storageos.db.client.model.ProtectionSystem)

Example 24 with ProtectionSystem

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

the class ProtectionSystemService method getProtectionSystems.

/**
 * Gets the id, name, and self link for all registered protection systems.
 *
 * @brief List protection systems
 * @return A reference to a ProtectionSystemList.
 */
@GET
@Produces({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON })
@CheckPermission(roles = { Role.SYSTEM_ADMIN, Role.SYSTEM_MONITOR })
public ProtectionSystemList getProtectionSystems() {
    ProtectionSystemList systemsList = new ProtectionSystemList();
    ProtectionSystem system = null;
    List<URI> ids = _dbClient.queryByType(ProtectionSystem.class, true);
    for (URI id : ids) {
        system = _dbClient.queryObject(ProtectionSystem.class, id);
        if (system != null && RegistrationStatus.REGISTERED.toString().equalsIgnoreCase(system.getRegistrationStatus())) {
            systemsList.getSystems().add(toNamedRelatedResource(system));
        }
    }
    return systemsList;
}
Also used : ProtectionSystemList(com.emc.storageos.model.protection.ProtectionSystemList) MapProtectionSystem(com.emc.storageos.api.mapper.functions.MapProtectionSystem) ProtectionSystem(com.emc.storageos.db.client.model.ProtectionSystem) URI(java.net.URI) Produces(javax.ws.rs.Produces) GET(javax.ws.rs.GET) CheckPermission(com.emc.storageos.security.authorization.CheckPermission)

Example 25 with ProtectionSystem

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

the class ProtectionSystemService method deleteProtectionSystem.

/**
 * Deactivate protection system, this will move it to a "marked-for-delete" state.
 * It will be deleted in the next iteration of garbage collector
 *
 * @param id the URN of a ViPR protection system
 * @brief Delete protection system
 * @return No data returned in response body
 */
@POST
@Produces({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON })
@Path("/{id}/deactivate")
@CheckPermission(roles = { Role.SYSTEM_ADMIN, Role.RESTRICTED_SYSTEM_ADMIN })
public Response deleteProtectionSystem(@PathParam("id") URI id) {
    ArgValidator.checkFieldUriType(id, ProtectionSystem.class, "id");
    ProtectionSystem system = _dbClient.queryObject(ProtectionSystem.class, id);
    ArgValidator.checkEntityNotNull(system, id, isIdEmbeddedInURL(id));
    // Check to make sure there are no volumes associated with this protection system
    List<ProtectionSet> protectionSetsToDelete = new ArrayList<ProtectionSet>();
    if (checkForVolumes(id, protectionSetsToDelete)) {
        // don't allow the delete protection system if there are volumes
        throw APIException.badRequests.unableToDeactivateDueToDependencies(id);
    }
    // delete any empty protection sets
    _dbClient.markForDeletion(protectionSetsToDelete);
    // Side-effect: RPSiteArray entries need to be cleaned up so placement and connectivity feeds are correct
    // Mark all of the RPSiteArray entries associated with this protection system for deletion
    URIQueryResultList sitelist = new URIQueryResultList();
    _dbClient.queryByConstraint(AlternateIdConstraint.Factory.getRPSiteArrayProtectionSystemConstraint(id.toString()), sitelist);
    Iterator<URI> it = sitelist.iterator();
    while (it.hasNext()) {
        URI rpSiteArrayId = it.next();
        RPSiteArray siteArray = _dbClient.queryObject(RPSiteArray.class, rpSiteArrayId);
        if (siteArray != null) {
            _dbClient.markForDeletion(siteArray);
        }
    }
    _dbClient.markForDeletion(system);
    auditOp(OperationTypeEnum.DELETE_PROTECTION_SYSTEM, true, null, system.getId().toString());
    return Response.ok().build();
}
Also used : RPSiteArray(com.emc.storageos.db.client.model.RPSiteArray) ProtectionSet(com.emc.storageos.db.client.model.ProtectionSet) ArrayList(java.util.ArrayList) MapProtectionSystem(com.emc.storageos.api.mapper.functions.MapProtectionSystem) ProtectionSystem(com.emc.storageos.db.client.model.ProtectionSystem) URI(java.net.URI) URIQueryResultList(com.emc.storageos.db.client.constraint.URIQueryResultList) Path(javax.ws.rs.Path) POST(javax.ws.rs.POST) Produces(javax.ws.rs.Produces) CheckPermission(com.emc.storageos.security.authorization.CheckPermission)

Aggregations

ProtectionSystem (com.emc.storageos.db.client.model.ProtectionSystem)120 URI (java.net.URI)57 ArrayList (java.util.ArrayList)52 NamedURI (com.emc.storageos.db.client.model.NamedURI)44 Volume (com.emc.storageos.db.client.model.Volume)44 HashMap (java.util.HashMap)32 StringSet (com.emc.storageos.db.client.model.StringSet)30 StorageSystem (com.emc.storageos.db.client.model.StorageSystem)28 DatabaseException (com.emc.storageos.db.exceptions.DatabaseException)25 InternalException (com.emc.storageos.svcs.errorhandling.resources.InternalException)25 ControllerException (com.emc.storageos.volumecontroller.ControllerException)25 RPProtectionRecommendation (com.emc.storageos.volumecontroller.RPProtectionRecommendation)25 URISyntaxException (java.net.URISyntaxException)25 DeviceControllerException (com.emc.storageos.exceptions.DeviceControllerException)24 RecoverPointException (com.emc.storageos.recoverpoint.exceptions.RecoverPointException)24 InternalServerErrorException (com.emc.storageos.svcs.errorhandling.resources.InternalServerErrorException)24 WorkflowException (com.emc.storageos.workflow.WorkflowException)24 Test (org.junit.Test)24 FunctionalAPIActionFailedException_Exception (com.emc.fapiclient.ws.FunctionalAPIActionFailedException_Exception)23 FunctionalAPIInternalError_Exception (com.emc.fapiclient.ws.FunctionalAPIInternalError_Exception)23