Search in sources :

Example 6 with SelectorOptions

use of com.evolveum.midpoint.schema.SelectorOptions in project midpoint by Evolveum.

the class CertificationManagerImpl method getCampaignStatistics.

// this method delegates the authorization to the model
@Override
public AccessCertificationCasesStatisticsType getCampaignStatistics(String campaignOid, boolean currentStageOnly, Task task, OperationResult parentResult) throws ObjectNotFoundException, SchemaException, SecurityViolationException, ObjectAlreadyExistsException {
    Validate.notNull(campaignOid, "campaignOid");
    Validate.notNull(task, "task");
    Validate.notNull(parentResult, "parentResult");
    OperationResult result = parentResult.createSubresult(OPERATION_GET_CAMPAIGN_STATISTICS);
    try {
        AccessCertificationCasesStatisticsType stat = new AccessCertificationCasesStatisticsType(prismContext);
        Collection<SelectorOptions<GetOperationOptions>> options = SelectorOptions.createCollection(F_CASE, GetOperationOptions.createRetrieve());
        AccessCertificationCampaignType campaign;
        try {
            campaign = modelService.getObject(AccessCertificationCampaignType.class, campaignOid, options, task, parentResult).asObjectable();
        } catch (CommunicationException | ConfigurationException | ExpressionEvaluationException e) {
            throw new SystemException("Unexpected exception while getting campaign object: " + e.getMessage(), e);
        }
        int accept = 0, revoke = 0, revokeRemedied = 0, reduce = 0, reduceRemedied = 0, noDecision = 0, noResponse = 0;
        for (AccessCertificationCaseType _case : campaign.getCase()) {
            AccessCertificationResponseType outcome;
            if (currentStageOnly) {
                if (_case.getStageNumber() == campaign.getStageNumber()) {
                    outcome = OutcomeUtils.fromUri(_case.getCurrentStageOutcome());
                } else {
                    continue;
                }
            } else {
                outcome = OutcomeUtils.fromUri(_case.getOutcome());
            }
            if (outcome == null) {
                outcome = AccessCertificationResponseType.NO_RESPONSE;
            }
            switch(outcome) {
                case ACCEPT:
                    accept++;
                    break;
                case REVOKE:
                    revoke++;
                    if (_case.getRemediedTimestamp() != null) {
                        revokeRemedied++;
                    }
                    break;
                case REDUCE:
                    reduce++;
                    if (_case.getRemediedTimestamp() != null) {
                        // currently not possible
                        reduceRemedied++;
                    }
                    break;
                case NOT_DECIDED:
                    noDecision++;
                    break;
                case NO_RESPONSE:
                    noResponse++;
                    break;
                default:
                    throw new IllegalStateException("Unexpected outcome: " + outcome);
            }
        }
        stat.setMarkedAsAccept(accept);
        stat.setMarkedAsRevoke(revoke);
        stat.setMarkedAsRevokeAndRemedied(revokeRemedied);
        stat.setMarkedAsReduce(reduce);
        stat.setMarkedAsReduceAndRemedied(reduceRemedied);
        stat.setMarkedAsNotDecide(noDecision);
        stat.setWithoutResponse(noResponse);
        return stat;
    } catch (RuntimeException e) {
        result.recordFatalError("Couldn't get campaign statistics: unexpected exception: " + e.getMessage(), e);
        throw e;
    } finally {
        result.computeStatusIfUnknown();
    }
}
Also used : OperationResult(com.evolveum.midpoint.schema.result.OperationResult) SelectorOptions(com.evolveum.midpoint.schema.SelectorOptions)

Example 7 with SelectorOptions

use of com.evolveum.midpoint.schema.SelectorOptions in project midpoint by Evolveum.

the class ProjectionValuesProcessor method processProjections.

private <F extends FocusType> void processProjections(LensContext<F> context, LensProjectionContext projContext, String activityDescription, Task task, OperationResult result) throws SchemaException, ExpressionEvaluationException, ObjectNotFoundException, ObjectAlreadyExistsException, CommunicationException, ConfigurationException, SecurityViolationException, PolicyViolationException {
    checkSchemaAndPolicies(context, projContext, activityDescription, result);
    SynchronizationPolicyDecision policyDecision = projContext.getSynchronizationPolicyDecision();
    if (policyDecision != null && policyDecision == SynchronizationPolicyDecision.UNLINK) {
        // we cannot skip deleted accounts here as the delete delta will be skipped as well
        if (LOGGER.isTraceEnabled()) {
            LOGGER.trace("Skipping processing of value for {} because the decision is {}", projContext.getHumanReadableName(), policyDecision);
        }
        return;
    }
    if (consistencyChecks)
        context.checkConsistence();
    if (!projContext.hasFullShadow() && hasIterationExpression(projContext)) {
        contextLoader.loadFullShadow(context, projContext, "iteration expression", task, result);
        if (projContext.getSynchronizationPolicyDecision() == SynchronizationPolicyDecision.BROKEN) {
            return;
        }
    }
    int maxIterations = determineMaxIterations(projContext);
    int iteration = 0;
    String iterationToken = null;
    boolean wasResetIterationCounter = false;
    PrismObject<ShadowType> shadowCurrent = projContext.getObjectCurrent();
    if (shadowCurrent != null) {
        Integer shadowIteration = shadowCurrent.asObjectable().getIteration();
        if (shadowIteration != null) {
            iteration = shadowIteration;
        }
        iterationToken = shadowCurrent.asObjectable().getIterationToken();
    }
    boolean skipUniquenessCheck = false;
    while (true) {
        projContext.setIteration(iteration);
        if (iterationToken == null) {
            iterationToken = formatIterationToken(context, projContext, iteration, task, result);
        }
        projContext.setIterationToken(iterationToken);
        String conflictMessage;
        // These are normally null. But there may be leftover from the previous iteration.
        // While that should not affect the algorithm (it should overwrite it) it may confuse
        // people during debugging and unecessarily clutter the debug output.
        projContext.setOutboundConstruction(null);
        projContext.setSqueezedAttributes(null);
        projContext.setSqueezedAssociations(null);
        LOGGER.trace("Projection values iteration {}, token '{}' for {}", iteration, iterationToken, projContext.getHumanReadableName());
        if (!evaluateIterationCondition(context, projContext, iteration, iterationToken, true, task, result)) {
            conflictMessage = "pre-iteration condition was false";
            LOGGER.debug("Skipping iteration {}, token '{}' for {} because the pre-iteration condition was false", iteration, iterationToken, projContext.getHumanReadableName());
        } else {
            if (consistencyChecks)
                context.checkConsistence();
            // Re-evaluates the values in the account constructions (including roles)
            assignmentProcessor.processAssignmentsAccountValues(projContext, result);
            context.recompute();
            if (consistencyChecks)
                context.checkConsistence();
            //				LensUtil.traceContext(LOGGER, activityDescription, "values (assignment account values)", false, context, true);
            // Evaluates the values in outbound mappings
            outboundProcessor.processOutbound(context, projContext, task, result);
            context.recompute();
            if (consistencyChecks)
                context.checkConsistence();
            //				LensUtil.traceContext(LOGGER, activityDescription, "values (outbound)", false, context, true);
            // Merges the values together, processing exclusions and strong/weak mappings are needed
            consolidationProcessor.consolidateValues(context, projContext, task, result);
            if (consistencyChecks)
                context.checkConsistence();
            context.recompute();
            if (consistencyChecks)
                context.checkConsistence();
            // Aux object classes may have changed during consolidation. Make sure we have up-to-date definitions.
            context.refreshAuxiliaryObjectClassDefinitions();
            // but I don't see any easier way to do it now.
            if (iteration != 0 && !wasResetIterationCounter && willResetIterationCounter(projContext)) {
                wasResetIterationCounter = true;
                iteration = 0;
                iterationToken = null;
                cleanupContext(projContext);
                LOGGER.trace("Resetting iteration counter and token because we have rename");
                if (consistencyChecks)
                    context.checkConsistence();
                continue;
            }
            if (policyDecision != null && policyDecision == SynchronizationPolicyDecision.DELETE) {
                // No need to play the iterative game if the account is deleted
                break;
            }
            // Check constraints
            boolean conflict = true;
            ShadowConstraintsChecker<F> checker = new ShadowConstraintsChecker<F>(projContext);
            if (skipUniquenessCheck) {
                skipUniquenessCheck = false;
                conflict = false;
            } else {
                checker.setPrismContext(prismContext);
                checker.setContext(context);
                checker.setProvisioningService(provisioningService);
                checker.check(task, result);
                if (checker.isSatisfiesConstraints()) {
                    LOGGER.trace("Current shadow satisfies uniqueness constraints. Iteration {}, token '{}'", iteration, iterationToken);
                    conflict = false;
                } else {
                    LOGGER.trace("Current shadow does not satisfy constraints. Conflicting shadow exists. Needed to found out what's wrong.");
                    if (checker.getConflictingShadow() != null) {
                        PrismObject<ShadowType> fullConflictingShadow = null;
                        try {
                            Collection<SelectorOptions<GetOperationOptions>> options = SelectorOptions.createCollection(GetOperationOptions.createPointInTimeType(PointInTimeType.FUTURE));
                            fullConflictingShadow = provisioningService.getObject(ShadowType.class, checker.getConflictingShadow().getOid(), options, task, result);
                        } catch (ObjectNotFoundException ex) {
                            //if object not found exception occurred, its ok..the account was deleted by the discovery, so there esits no more conflicting shadow
                            LOGGER.trace("Conflicting shadow was deleted by discovery. It does not exist anymore. Continue with adding current shadow.");
                            conflict = false;
                        }
                        result.computeStatus();
                        // the situation which happend
                        if (result.isError()) {
                            result.muteError();
                        }
                        if (conflict) {
                            PrismObject<F> focus = repositoryService.searchShadowOwner(checker.getConflictingShadow().getOid(), SelectorOptions.createCollection(GetOperationOptions.createAllowNotFound()), result);
                            //the owner of the shadow exist and it is a current user..so the shadow was successfully created, linked etc..no other recompute is needed..
                            if (focus != null && focus.getOid().equals(context.getFocusContext().getOid())) {
                                LOGGER.trace("Conflicting projection already linked to the current focus, no recompute needed, continue processing with conflicting projection.");
                                //	        			accountContext.setSecondaryDelta(null);
                                cleanupContext(projContext);
                                projContext.setSynchronizationPolicyDecision(SynchronizationPolicyDecision.KEEP);
                                projContext.setObjectOld(fullConflictingShadow.clone());
                                projContext.setObjectCurrent(fullConflictingShadow);
                                projContext.setFullShadow(true);
                                ObjectDelta<ShadowType> secondaryDelta = projContext.getSecondaryDelta();
                                if (secondaryDelta != null && projContext.getOid() != null) {
                                    secondaryDelta.setOid(projContext.getOid());
                                }
                                //				        			result.computeStatus();
                                //									// if the result is fatal error, it may mean that the
                                //									// already exists expection occures before..but in this
                                //									// scenario it means, the exception was handled and we
                                //									// can mute the result to give better understanding of
                                //									// the situation which happend
                                //				        			if (result.isError()){
                                //				        				result.muteError();
                                //				        			}
                                // Re-do this same iteration again (do not increase iteration count).
                                // It will recompute the values and therefore enforce the user deltas and enable reconciliation
                                // to avoid endless loop
                                skipUniquenessCheck = true;
                                continue;
                            }
                            if (focus == null) {
                                LOGGER.trace("There is no owner linked with the conflicting projection.");
                                ResourceType resourceType = projContext.getResource();
                                if (ResourceTypeUtil.isSynchronizationOpportunistic(resourceType)) {
                                    LOGGER.trace("Trying to find owner using correlation expression.");
                                    boolean match = synchronizationService.matchUserCorrelationRule(fullConflictingShadow, context.getFocusContext().getObjectNew(), resourceType, context.getSystemConfiguration(), task, result);
                                    if (match) {
                                        if (projContext.getPrimaryDelta() != null && projContext.getPrimaryDelta().isAdd()) {
                                            PrismObject<ShadowType> shadow = projContext.getPrimaryDelta().getObjectToAdd();
                                            LOGGER.trace("Found primary ADD delta of shadow {}.", shadow);
                                            LensProjectionContext conflictingAccountContext = context.findProjectionContext(projContext.getResourceShadowDiscriminator(), fullConflictingShadow.getOid());
                                            if (conflictingAccountContext == null) {
                                                conflictingAccountContext = LensUtil.createAccountContext(context, projContext.getResourceShadowDiscriminator());
                                                //													conflictingAccountContext = context.createProjectionContext(accountContext.getResourceShadowDiscriminator());
                                                conflictingAccountContext.setOid(fullConflictingShadow.getOid());
                                                conflictingAccountContext.setObjectOld(fullConflictingShadow.clone());
                                                conflictingAccountContext.setObjectCurrent(fullConflictingShadow);
                                                conflictingAccountContext.setFullShadow(true);
                                                conflictingAccountContext.setSynchronizationPolicyDecision(SynchronizationPolicyDecision.KEEP);
                                                conflictingAccountContext.setResource(projContext.getResource());
                                                conflictingAccountContext.setDoReconciliation(true);
                                                conflictingAccountContext.getDependencies().clear();
                                                conflictingAccountContext.getDependencies().addAll(projContext.getDependencies());
                                                conflictingAccountContext.setWave(projContext.getWave());
                                                context.addConflictingProjectionContext(conflictingAccountContext);
                                            }
                                            projContext.setSynchronizationPolicyDecision(SynchronizationPolicyDecision.BROKEN);
                                            result.recordFatalError("Could not add account " + projContext.getObjectNew() + ", because the account with the same identifier already exists on the resource. ");
                                            LOGGER.error("Could not add account {}, because the account with the same identifier already exists on the resource. ", projContext.getObjectNew());
                                            // to avoid endless loop
                                            skipUniquenessCheck = true;
                                            continue;
                                        }
                                        //found shadow belongs to the current user..need to link it and replace current shadow with the found shadow..
                                        cleanupContext(projContext);
                                        projContext.setObjectOld(fullConflictingShadow.clone());
                                        projContext.setObjectCurrent(fullConflictingShadow);
                                        projContext.setFullShadow(true);
                                        projContext.setSynchronizationPolicyDecision(SynchronizationPolicyDecision.KEEP);
                                        ObjectDelta<ShadowType> secondaryDelta = projContext.getSecondaryDelta();
                                        if (secondaryDelta != null && projContext.getOid() != null) {
                                            secondaryDelta.setOid(projContext.getOid());
                                        }
                                        LOGGER.trace("User {} satisfies correlation rules.", context.getFocusContext().getObjectNew());
                                        // Re-do this same iteration again (do not increase iteration count).
                                        // It will recompute the values and therefore enforce the user deltas and enable reconciliation
                                        // to avoid endless loop
                                        skipUniquenessCheck = true;
                                        continue;
                                    } else {
                                        LOGGER.trace("User {} does not satisfy correlation rules.", context.getFocusContext().getObjectNew());
                                    }
                                }
                            } else {
                                LOGGER.trace("Recomputing shadow identifier, because shadow with the some identifier exists and it belongs to other user.");
                            }
                        }
                    }
                }
            }
            if (!conflict) {
                if (evaluateIterationCondition(context, projContext, iteration, iterationToken, false, task, result)) {
                    // stop the iterations
                    break;
                } else {
                    conflictMessage = "post-iteration condition was false";
                    LOGGER.debug("Skipping iteration {}, token '{}' for {} because the post-iteration condition was false", new Object[] { iteration, iterationToken, projContext.getHumanReadableName() });
                }
            } else {
                conflictMessage = checker.getMessages();
            }
        }
        iteration++;
        iterationToken = null;
        LensUtil.checkMaxIterations(iteration, maxIterations, conflictMessage, projContext.getHumanReadableName());
        cleanupContext(projContext);
        if (consistencyChecks)
            context.checkConsistence();
    }
    addIterationTokenDeltas(projContext);
    result.cleanupResult();
    if (consistencyChecks)
        context.checkConsistence();
}
Also used : ShadowType(com.evolveum.midpoint.xml.ns._public.common.common_3.ShadowType) LensProjectionContext(com.evolveum.midpoint.model.impl.lens.LensProjectionContext) ResourceType(com.evolveum.midpoint.xml.ns._public.common.common_3.ResourceType) SynchronizationPolicyDecision(com.evolveum.midpoint.model.api.context.SynchronizationPolicyDecision) SelectorOptions(com.evolveum.midpoint.schema.SelectorOptions) ObjectNotFoundException(com.evolveum.midpoint.util.exception.ObjectNotFoundException)

Example 8 with SelectorOptions

use of com.evolveum.midpoint.schema.SelectorOptions in project midpoint by Evolveum.

the class ContextLoader method loadFullShadow.

public <F extends ObjectType> void loadFullShadow(LensContext<F> context, LensProjectionContext projCtx, String reason, Task task, OperationResult result) throws ObjectNotFoundException, CommunicationException, SchemaException, ConfigurationException, SecurityViolationException, ExpressionEvaluationException {
    if (projCtx.isFullShadow()) {
        // already loaded
        return;
    }
    if (projCtx.isAdd() && projCtx.getOid() == null) {
        // nothing to load yet
        return;
    }
    if (projCtx.isThombstone()) {
        // loading is futile
        return;
    }
    ResourceShadowDiscriminator discr = projCtx.getResourceShadowDiscriminator();
    if (discr != null && discr.getOrder() > 0) {
        // It may be just too early to load the projection
        if (LensUtil.hasLowerOrderContext(context, projCtx) && (context.getExecutionWave() < projCtx.getWave())) {
            // We cannot reliably load the context now
            return;
        }
    }
    GetOperationOptions getOptions = GetOperationOptions.createAllowNotFound();
    getOptions.setPointInTimeType(PointInTimeType.FUTURE);
    if (SchemaConstants.CHANGE_CHANNEL_DISCOVERY_URI.equals(context.getChannel())) {
        LOGGER.trace("Loading full resource object {} from provisioning - with doNotDiscover to avoid loops; reason: {}", projCtx, reason);
        // Avoid discovery loops
        getOptions.setDoNotDiscovery(true);
    } else {
        LOGGER.trace("Loading full resource object {} from provisioning (discovery enabled), reason: {}, channel: {}", projCtx, reason, context.getChannel());
    }
    try {
        Collection<SelectorOptions<GetOperationOptions>> options = SelectorOptions.createCollection(getOptions);
        applyAttributesToGet(projCtx, options);
        PrismObject<ShadowType> objectCurrent = provisioningService.getObject(ShadowType.class, projCtx.getOid(), options, task, result);
        Validate.notNull(objectCurrent.getOid());
        // TODO: use setLoadedObject() instead?
        projCtx.setObjectCurrent(objectCurrent);
        ShadowType oldShadow = objectCurrent.asObjectable();
        projCtx.determineFullShadowFlag(oldShadow.getFetchResult());
        // The getObject may return different OID than we have requested in case that compensation happened
        // TODO: this probably need to be fixed in the consistency mechanism
        // TODO: the following line is a temporary fix
        projCtx.setOid(objectCurrent.getOid());
    } catch (ObjectNotFoundException ex) {
        LOGGER.trace("Load of full resource object {} ended with ObjectNotFoundException (options={})", projCtx, getOptions);
        if (projCtx.isDelete()) {
            //this is OK, shadow was deleted, but we will continue in processing with old shadow..and set it as full so prevent from other full loading
            projCtx.setFullShadow(true);
        } else {
            boolean compensated = false;
            if (!GetOperationOptions.isDoNotDiscovery(getOptions)) {
                // The account might have been re-created by the discovery.
                // Reload focus, try to find out if there is a new matching link (and the old is gone)
                LensFocusContext<F> focusContext = context.getFocusContext();
                if (focusContext != null) {
                    Class<F> focusClass = focusContext.getObjectTypeClass();
                    if (FocusType.class.isAssignableFrom(focusClass)) {
                        LOGGER.trace("Reloading focus to check for new links");
                        PrismObject<F> focusCurrent = cacheRepositoryService.getObject(focusContext.getObjectTypeClass(), focusContext.getOid(), null, result);
                        FocusType focusType = (FocusType) focusCurrent.asObjectable();
                        for (ObjectReferenceType linkRef : focusType.getLinkRef()) {
                            if (linkRef.getOid().equals(projCtx.getOid())) {
                                // The deleted shadow is still in the linkRef. This should not happen, but it obviously happens sometimes.
                                // Maybe some strange race condition? Anyway, we want a robust behavior and this linkeRef should NOT be there.
                                // So simple remove it.
                                LOGGER.warn("The OID " + projCtx.getOid() + " of deleted shadow still exists in the linkRef after discovery (" + focusCurrent + "), removing it");
                                ReferenceDelta unlinkDelta = ReferenceDelta.createModificationDelete(FocusType.F_LINK_REF, focusContext.getObjectDefinition(), linkRef.asReferenceValue().clone());
                                focusContext.swallowToSecondaryDelta(unlinkDelta);
                                continue;
                            }
                            boolean found = false;
                            for (LensProjectionContext pCtx : context.getProjectionContexts()) {
                                if (linkRef.getOid().equals(pCtx.getOid())) {
                                    found = true;
                                    break;
                                }
                            }
                            if (!found) {
                                // This link is new, it is not in the existing lens context
                                PrismObject<ShadowType> newLinkRepoShadow = cacheRepositoryService.getObject(ShadowType.class, linkRef.getOid(), null, result);
                                if (ShadowUtil.matches(newLinkRepoShadow, projCtx.getResourceShadowDiscriminator())) {
                                    LOGGER.trace("Found new matching link: {}, updating projection context", newLinkRepoShadow);
                                    // MID-3317
                                    LOGGER.trace("Applying definition from provisioning first.");
                                    provisioningService.applyDefinition(newLinkRepoShadow, task, result);
                                    projCtx.setObjectCurrent(newLinkRepoShadow);
                                    projCtx.setOid(newLinkRepoShadow.getOid());
                                    projCtx.recompute();
                                    compensated = true;
                                    break;
                                } else {
                                    LOGGER.trace("Found new link: {}, but skipping it because it does not match the projection context", newLinkRepoShadow);
                                }
                            }
                        }
                    }
                }
            }
            if (!compensated) {
                LOGGER.trace("ObjectNotFound error is not compensated, setting context to thombstone");
                projCtx.getResourceShadowDiscriminator().setThombstone(true);
                projCtx.setExists(false);
                projCtx.setFullShadow(false);
            }
        }
    }
    projCtx.recompute();
    if (LOGGER.isTraceEnabled()) {
        LOGGER.trace("Loaded full resource object:\n{}", projCtx.debugDump(1));
    }
}
Also used : LensProjectionContext(com.evolveum.midpoint.model.impl.lens.LensProjectionContext) ReferenceDelta(com.evolveum.midpoint.prism.delta.ReferenceDelta) PrismObject(com.evolveum.midpoint.prism.PrismObject) GetOperationOptions(com.evolveum.midpoint.schema.GetOperationOptions) SelectorOptions(com.evolveum.midpoint.schema.SelectorOptions) ObjectNotFoundException(com.evolveum.midpoint.util.exception.ObjectNotFoundException) ResourceShadowDiscriminator(com.evolveum.midpoint.schema.ResourceShadowDiscriminator) LensFocusContext(com.evolveum.midpoint.model.impl.lens.LensFocusContext)

Example 9 with SelectorOptions

use of com.evolveum.midpoint.schema.SelectorOptions in project midpoint by Evolveum.

the class ContextLoader method finishLoadOfProjectionContext.

/**
	 * Check reconcile flag in account sync context and set accountOld
     * variable if it's not set (from provisioning), load resource (if not set already), etc.
	 */
private <F extends ObjectType> void finishLoadOfProjectionContext(LensContext<F> context, LensProjectionContext projContext, Task task, OperationResult result) throws ObjectNotFoundException, CommunicationException, SchemaException, ConfigurationException, SecurityViolationException, ExpressionEvaluationException {
    String projectionHumanReadableName = projContext.getHumanReadableName();
    if (projContext.getSynchronizationPolicyDecision() == SynchronizationPolicyDecision.BROKEN) {
        return;
    }
    // MID-2436 (volatile objects) - as a quick but effective hack, we set reconciliation:=TRUE for volatile accounts
    ResourceObjectTypeDefinitionType objectDefinition = projContext.getResourceObjectTypeDefinitionType();
    if (objectDefinition != null && objectDefinition.getVolatility() == ResourceObjectVolatilityType.UNPREDICTABLE && !projContext.isDoReconciliation()) {
        LOGGER.trace("Resource object volatility is UNPREDICTABLE => setting doReconciliation to TRUE for {}", projContext.getResourceShadowDiscriminator());
        projContext.setDoReconciliation(true);
    }
    // Remember OID before the object could be wiped
    String projectionObjectOid = projContext.getOid();
    if (projContext.isDoReconciliation() && !projContext.isFullShadow()) {
        // The current object is useless here. So lets just wipe it so it will get loaded
        projContext.setObjectCurrent(null);
    }
    // Load current object
    boolean thombstone = false;
    PrismObject<ShadowType> projectionObject = projContext.getObjectCurrent();
    if (projContext.getObjectCurrent() == null || needToReload(context, projContext)) {
        if (projContext.isAdd()) {
            // No need to load old object, there is none
            projContext.setExists(false);
            projContext.recompute();
            projectionObject = projContext.getObjectNew();
        } else {
            if (projectionObjectOid == null) {
                projContext.setExists(false);
                if (projContext.getResourceShadowDiscriminator() == null || projContext.getResourceShadowDiscriminator().getResourceOid() == null) {
                    throw new SystemException("Projection " + projectionHumanReadableName + " with null OID, no representation and no resource OID in account sync context " + projContext);
                }
            } else {
                projContext.setExists(true);
                GetOperationOptions rootOptions = GetOperationOptions.createPointInTimeType(PointInTimeType.FUTURE);
                if (projContext.isDoReconciliation()) {
                    if (SchemaConstants.CHANGE_CHANNEL_DISCOVERY_URI.equals(context.getChannel())) {
                        // Avoid discovery loops
                        rootOptions.setDoNotDiscovery(true);
                    }
                } else {
                    rootOptions.setNoFetch(true);
                }
                rootOptions.setAllowNotFound(true);
                Collection<SelectorOptions<GetOperationOptions>> options = SelectorOptions.createCollection(rootOptions);
                if (LOGGER.isTraceEnabled()) {
                    LOGGER.trace("Loading shadow {} for projection {}, options={}", projectionObjectOid, projectionHumanReadableName, options);
                }
                try {
                    PrismObject<ShadowType> objectOld = provisioningService.getObject(projContext.getObjectTypeClass(), projectionObjectOid, options, task, result);
                    if (LOGGER.isTraceEnabled()) {
                        if (!GetOperationOptions.isNoFetch(rootOptions) && !GetOperationOptions.isRaw(rootOptions)) {
                            if (LOGGER.isTraceEnabled()) {
                                LOGGER.trace("Full shadow loaded for {}:\n{}", projectionHumanReadableName, objectOld.debugDump(1));
                            }
                        }
                    }
                    Validate.notNull(objectOld.getOid());
                    if (InternalsConfig.consistencyChecks) {
                        String resourceOid = projContext.getResourceOid();
                        if (resourceOid != null && !resourceOid.equals(objectOld.asObjectable().getResourceRef().getOid())) {
                            throw new IllegalStateException("Loaded shadow with wrong resourceRef. Loading shadow " + projectionObjectOid + ", got " + objectOld.getOid() + ", expected resourceRef " + resourceOid + ", but was " + objectOld.asObjectable().getResourceRef().getOid() + " for context " + projectionHumanReadableName);
                        }
                    }
                    projContext.setLoadedObject(objectOld);
                    ShadowType oldShadow = objectOld.asObjectable();
                    if (projContext.isDoReconciliation()) {
                        projContext.determineFullShadowFlag(oldShadow.getFetchResult());
                    } else {
                        projContext.setFullShadow(false);
                    }
                    projectionObject = objectOld;
                } catch (ObjectNotFoundException ex) {
                    // This does not mean BROKEN. The projection was there, but it gone now. What we really want here
                    // is a thombstone projection.
                    thombstone = true;
                    projContext.setFullShadow(false);
                    LOGGER.warn("Could not find object with oid {}. The projection context {} is marked as thombstone.", projectionObjectOid, projectionHumanReadableName);
                } catch (CommunicationException | SchemaException | ConfigurationException | SecurityViolationException | RuntimeException | Error e) {
                    LOGGER.warn("Problem while getting object with oid {}. Projection context {} is marked as broken: {}: {}", projectionObjectOid, projectionHumanReadableName, e.getClass().getSimpleName(), e.getMessage());
                    projContext.setSynchronizationPolicyDecision(SynchronizationPolicyDecision.BROKEN);
                    ResourceType resourceType = projContext.getResource();
                    if (resourceType == null) {
                        throw e;
                    } else {
                        ErrorSelectorType errorSelector = null;
                        if (resourceType.getConsistency() != null) {
                            errorSelector = resourceType.getConsistency().getConnectorErrorCriticality();
                        }
                        if (errorSelector == null) {
                            if (e instanceof SchemaException) {
                                // We cannot do any better.
                                return;
                            } else {
                                throw e;
                            }
                        } else {
                            if (ExceptionUtil.isSelected(errorSelector, e)) {
                                throw e;
                            } else {
                                return;
                            }
                        }
                    }
                }
            }
            projContext.setFresh(true);
        }
    } else {
        projectionObject = projContext.getObjectCurrent();
        if (projectionObjectOid != null) {
            projContext.setExists(true);
        }
    }
    // Determine Resource
    ResourceType resourceType = projContext.getResource();
    String resourceOid = null;
    if (resourceType == null) {
        if (projectionObject != null) {
            ShadowType shadowType = projectionObject.asObjectable();
            resourceOid = ShadowUtil.getResourceOid(shadowType);
        } else if (projContext.getResourceShadowDiscriminator() != null) {
            resourceOid = projContext.getResourceShadowDiscriminator().getResourceOid();
        } else if (!thombstone) {
            throw new IllegalStateException("No shadow, no discriminator and not thombstone? That won't do. Projection " + projectionHumanReadableName);
        }
    } else {
        resourceOid = resourceType.getOid();
    }
    // Determine discriminator
    ResourceShadowDiscriminator discr = projContext.getResourceShadowDiscriminator();
    if (discr == null) {
        if (projectionObject != null) {
            ShadowType accountShadowType = projectionObject.asObjectable();
            String intent = ShadowUtil.getIntent(accountShadowType);
            ShadowKindType kind = ShadowUtil.getKind(accountShadowType);
            discr = new ResourceShadowDiscriminator(resourceOid, kind, intent, thombstone);
        } else {
            discr = new ResourceShadowDiscriminator(null, null, null, thombstone);
        }
        projContext.setResourceShadowDiscriminator(discr);
    } else {
        if (thombstone) {
            // We do not want to reset thombstone flag if it was set before
            discr.setThombstone(thombstone);
        }
    }
    // Load resource
    if (resourceType == null && resourceOid != null) {
        resourceType = LensUtil.getResourceReadOnly(context, resourceOid, provisioningService, task, result);
        projContext.setResource(resourceType);
    }
    //Determine refined schema and password policies for account type
    RefinedObjectClassDefinition structuralObjectClassDef = projContext.getStructuralObjectClassDefinition();
    if (structuralObjectClassDef != null) {
        ObjectReferenceType passwordPolicyRef = structuralObjectClassDef.getPasswordPolicy();
        if (passwordPolicyRef != null && passwordPolicyRef.getOid() != null) {
            PrismObject<ValuePolicyType> passwordPolicy = cacheRepositoryService.getObject(ValuePolicyType.class, passwordPolicyRef.getOid(), null, result);
            if (passwordPolicy != null) {
                projContext.setAccountPasswordPolicy(passwordPolicy.asObjectable());
            }
        }
    }
    //set limitation, e.g. if this projection context should be recomputed and processed by projector
    if (ModelExecuteOptions.isLimitPropagation(context.getOptions())) {
        if (context.getTriggeredResourceOid() != null) {
            if (!context.getTriggeredResourceOid().equals(resourceOid)) {
                projContext.setCanProject(false);
            }
        }
    }
    setPrimaryDeltaOldValue(projContext);
}
Also used : SecurityViolationException(com.evolveum.midpoint.util.exception.SecurityViolationException) RefinedObjectClassDefinition(com.evolveum.midpoint.common.refinery.RefinedObjectClassDefinition) GetOperationOptions(com.evolveum.midpoint.schema.GetOperationOptions) SystemException(com.evolveum.midpoint.util.exception.SystemException) ConfigurationException(com.evolveum.midpoint.util.exception.ConfigurationException) SchemaException(com.evolveum.midpoint.util.exception.SchemaException) CommunicationException(com.evolveum.midpoint.util.exception.CommunicationException) SelectorOptions(com.evolveum.midpoint.schema.SelectorOptions) ObjectNotFoundException(com.evolveum.midpoint.util.exception.ObjectNotFoundException) ResourceShadowDiscriminator(com.evolveum.midpoint.schema.ResourceShadowDiscriminator)

Example 10 with SelectorOptions

use of com.evolveum.midpoint.schema.SelectorOptions in project midpoint by Evolveum.

the class AbstractCertificationTest method getCampaignWithCases.

protected AccessCertificationCampaignType getCampaignWithCases(String campaignOid) throws ConfigurationException, ObjectNotFoundException, SchemaException, CommunicationException, SecurityViolationException, ExpressionEvaluationException {
    Task task = taskManager.createTaskInstance(AbstractModelIntegrationTest.class.getName() + ".getObject");
    OperationResult result = task.getResult();
    Collection<SelectorOptions<GetOperationOptions>> options = Arrays.asList(SelectorOptions.create(F_CASE, GetOperationOptions.createRetrieve(INCLUDE)));
    AccessCertificationCampaignType campaign = modelService.getObject(AccessCertificationCampaignType.class, campaignOid, options, task, result).asObjectable();
    result.computeStatus();
    TestUtil.assertSuccess(result);
    return campaign;
}
Also used : Task(com.evolveum.midpoint.task.api.Task) SelectorOptions(com.evolveum.midpoint.schema.SelectorOptions) OperationResult(com.evolveum.midpoint.schema.result.OperationResult)

Aggregations

SelectorOptions (com.evolveum.midpoint.schema.SelectorOptions)127 OperationResult (com.evolveum.midpoint.schema.result.OperationResult)106 Task (com.evolveum.midpoint.task.api.Task)82 Test (org.testng.annotations.Test)47 ObjectQuery (com.evolveum.midpoint.prism.query.ObjectQuery)34 GetOperationOptions (com.evolveum.midpoint.schema.GetOperationOptions)31 ShadowType (com.evolveum.midpoint.xml.ns._public.common.common_3.ShadowType)31 PrismObject (com.evolveum.midpoint.prism.PrismObject)28 ObjectNotFoundException (com.evolveum.midpoint.util.exception.ObjectNotFoundException)28 SchemaException (com.evolveum.midpoint.util.exception.SchemaException)28 ItemPath (com.evolveum.midpoint.prism.path.ItemPath)23 ResourceType (com.evolveum.midpoint.xml.ns._public.common.common_3.ResourceType)21 ArrayList (java.util.ArrayList)19 PolyString (com.evolveum.midpoint.prism.polystring.PolyString)17 QName (javax.xml.namespace.QName)17 ConfigurationException (com.evolveum.midpoint.util.exception.ConfigurationException)16 ExpressionEvaluationException (com.evolveum.midpoint.util.exception.ExpressionEvaluationException)16 CommunicationException (com.evolveum.midpoint.util.exception.CommunicationException)14 SecurityViolationException (com.evolveum.midpoint.util.exception.SecurityViolationException)14 ResultHandler (com.evolveum.midpoint.schema.ResultHandler)12