use of com.evolveum.midpoint.prism.util.ObjectDeltaObject in project midpoint by Evolveum.
the class TestExpressionUtil method createVariablesOdo.
private VariablesMap createVariablesOdo() throws SchemaException, IOException {
VariablesMap variables = new VariablesMap();
PrismObject<UserType> userOld = createUser();
ObjectDelta<UserType> delta = PrismTestUtil.getPrismContext().deltaFactory().object().createModificationReplaceProperty(UserType.class, userOld.getOid(), UserType.F_FULL_NAME, PrismTestUtil.createPolyString("Captain Jack Sparrow"));
ObjectDeltaObject<UserType> odo = new ObjectDeltaObject<>(userOld, delta, null, userOld.getDefinition());
odo.recompute();
variables.addVariableDefinition(ExpressionConstants.VAR_USER, odo, odo.getDefinition());
variables.addVariableDefinition(ExpressionConstants.VAR_FOCUS, odo, odo.getDefinition());
return variables;
}
use of com.evolveum.midpoint.prism.util.ObjectDeltaObject in project midpoint by Evolveum.
the class VariablesMap method addVariableDefinitions.
public void addVariableDefinitions(VariablesMap extraVariables, @NotNull Collection<String> exceptFor) {
for (Entry<String, TypedValue> entry : extraVariables.entrySet()) {
if (exceptFor.contains(entry.getKey())) {
continue;
}
TypedValue valueDef = entry.getValue();
Object value = valueDef.getValue();
if (!areDeltasAllowed() && value instanceof ObjectDeltaObject<?>) {
ObjectDeltaObject<?> odo = (ObjectDeltaObject<?>) value;
if (odo.getObjectDelta() != null) {
throw new IllegalArgumentException("Cannot use variables with deltas in addVariableDefinitions. Use addVariableDefinitionsOld or addVariableDefinitionsNew.");
}
value = odo.getOldObject();
}
put(entry.getKey(), valueDef.createTransformed(value));
if (extraVariables.isAlias(entry.getKey())) {
registerAlias(entry.getKey(), extraVariables.getAliasResolution(entry.getKey()));
}
}
}
use of com.evolveum.midpoint.prism.util.ObjectDeltaObject in project midpoint by Evolveum.
the class MappingTestEvaluator method createMappingBuilder.
public <T> MappingBuilder<PrismPropertyValue<T>, PrismPropertyDefinition<T>> createMappingBuilder(String filename, String testName, final ValuePolicyType policy, ItemPath defaultTargetPropertyPath, ObjectDelta<UserType> userDelta, PrismObject<UserType> userOld) throws SchemaException, IOException {
MappingType mappingType = PrismTestUtil.parseAtomicValue(new File(TEST_DIR, filename), MappingType.COMPLEX_TYPE);
MappingBuilder<PrismPropertyValue<T>, PrismPropertyDefinition<T>> mappingBuilder = mappingFactory.createMappingBuilder(mappingType, testName);
// Source context: user
PrismObjectDefinition<UserType> objectDefinition = prismContext.getSchemaRegistry().findObjectDefinitionByCompileTimeClass(UserType.class);
ObjectDeltaObject<UserType> userOdo = new ObjectDeltaObject<>(userOld, userDelta, null, objectDefinition);
userOdo.recompute();
mappingBuilder.sourceContext(userOdo);
// Variable $focus
mappingBuilder.addVariableDefinition(ExpressionConstants.VAR_FOCUS, userOdo);
mappingBuilder.addVariableDefinition(ExpressionConstants.VAR_USER, userOdo);
// Variable $projection
PrismObject<ShadowType> account = getAccount();
ObjectDeltaObject<ShadowType> accountOdo = new ObjectDeltaObject<>(account, null, null, account.getDefinition());
accountOdo.recompute();
mappingBuilder.addVariableDefinition(ExpressionConstants.VAR_PROJECTION, accountOdo);
mappingBuilder.addVariableDefinition(ExpressionConstants.VAR_ACCOUNT, accountOdo);
// Target context: user
PrismObjectDefinition<UserType> userDefinition = getUserDefinition();
mappingBuilder.targetContext(userDefinition);
mappingBuilder.valuePolicySupplier((result) -> policy);
// Default target
if (defaultTargetPropertyPath != null) {
PrismPropertyDefinition<T> targetDefDefinition = userDefinition.findItemDefinition(defaultTargetPropertyPath);
if (targetDefDefinition == null) {
throw new IllegalArgumentException("The item path '" + defaultTargetPropertyPath + "' does not have a definition in " + userDefinition);
}
mappingBuilder.defaultTargetDefinition(targetDefDefinition);
}
mappingBuilder.now(XmlTypeConverter.createXMLGregorianCalendar());
return mappingBuilder;
}
use of com.evolveum.midpoint.prism.util.ObjectDeltaObject in project midpoint by Evolveum.
the class PathExpressionResolver method resolve.
/**
* Main entry point.
*/
TypedValue<?> resolve(OperationResult result) throws SchemaException, ObjectNotFoundException, SecurityViolationException, CommunicationException, ConfigurationException, ExpressionEvaluationException {
TypedValue<?> root;
String topVarDesc;
if (variableName != null) {
topVarDesc = "variable " + variableName;
if (variables.containsKey(variableName)) {
root = variables.get(variableName);
} else {
throw new SchemaException("No variable with name " + variableName + " in " + shortDesc);
}
} else {
topVarDesc = "default context";
root = defaultContext;
}
if (root == null) {
return null;
}
if (relativePath.isEmpty()) {
return root;
}
// TODO reconsider this (see MID-7057).
if (normalizeValuesToDelete) {
root = normalizeValuesToDelete(root);
}
if (root.getValue() instanceof ObjectReferenceType) {
root = resolveReference(root, objectResolver, null, topVarDesc, shortDesc, task, result);
}
String lastPathSegmentName = relativePath.lastName().getLocalPart();
Object rootValue = root.getValue();
if (rootValue == null) {
return determineNullTypedValue(root);
} else if (rootValue instanceof Objectable) {
return determineTypedValue(((Objectable) rootValue).asPrismObject(), false, result);
} else if (rootValue instanceof PrismObject<?>) {
return determineTypedValue((PrismObject<?>) rootValue, false, result);
} else if (rootValue instanceof PrismContainer<?>) {
return determineTypedValue((PrismContainer<?>) rootValue, false, result);
} else if (rootValue instanceof PrismContainerValue<?>) {
return determineTypedValue((PrismContainerValue<?>) rootValue);
} else if (rootValue instanceof Item<?, ?>) {
// Except for container (which is handled above)
throw new SchemaException("Cannot apply path " + relativePath + " to " + root + " in " + shortDesc);
} else if (rootValue instanceof ObjectDeltaObject<?>) {
return determineTypedValueOdo(lastPathSegmentName, root);
} else if (rootValue instanceof ItemDeltaItem<?, ?>) {
return determineTypedValue((ItemDeltaItem<?, ?>) rootValue);
} else {
throw new IllegalArgumentException("Unexpected root " + rootValue + " (relative path:" + relativePath + ") in " + shortDesc);
}
}
use of com.evolveum.midpoint.prism.util.ObjectDeltaObject in project midpoint by Evolveum.
the class ProjectionCredentialsProcessor method processProjectionPasswordMapping.
private <F extends FocusType> void processProjectionPasswordMapping(LensContext<F> context, final LensProjectionContext projCtx, final SecurityPolicyType securityPolicy, XMLGregorianCalendar now, Task task, OperationResult result) throws ExpressionEvaluationException, ObjectNotFoundException, SchemaException, CommunicationException, ConfigurationException, SecurityViolationException {
LensFocusContext<F> focusContext = context.getFocusContext();
PrismObject<F> focusNew = focusContext.getObjectNew();
if (focusNew == null) {
// This must be a focus delete or something similar. No point in proceeding
LOGGER.trace("focusNew is null, skipping credentials processing");
return;
}
PrismObjectDefinition<ShadowType> accountDefinition = prismContext.getSchemaRegistry().findObjectDefinitionByCompileTimeClass(ShadowType.class);
PrismPropertyDefinition<ProtectedStringType> projPasswordPropertyDefinition = accountDefinition.findPropertyDefinition(SchemaConstants.PATH_PASSWORD_VALUE);
ResourceShadowDiscriminator rsd = projCtx.getResourceShadowDiscriminator();
ResourceObjectDefinition objectDefinition = projCtx.getStructuralObjectDefinition();
if (objectDefinition == null) {
LOGGER.trace("No ResourceObjectTypeDefinition, therefore also no password outbound definition," + " skipping credentials processing for projection {}", rsd);
return;
}
List<MappingType> outboundMappingBeans = objectDefinition.getPasswordOutbound();
if (outboundMappingBeans.isEmpty()) {
LOGGER.trace("No outbound password mapping for {}, skipping credentials processing", rsd);
return;
}
ObjectDeltaObject<F> objectDeltaObject = focusContext.getObjectDeltaObjectAbsolute();
// HACK
if (!projCtx.isDoReconciliation() && !projCtx.isAdd() && !isActivated(outboundMappingBeans, objectDeltaObject.getObjectDelta())) {
LOGGER.trace("Outbound password mappings not activated for type {}, skipping credentials processing", rsd);
return;
}
ObjectDelta<ShadowType> projDelta = projCtx.getCurrentDelta();
PropertyDelta<ProtectedStringType> projPasswordDelta;
if (projDelta != null && projDelta.getChangeType() == MODIFY) {
projPasswordDelta = projDelta.findPropertyDelta(SchemaConstants.PATH_PASSWORD_VALUE);
} else {
projPasswordDelta = null;
}
checkExistingDeltaSanity(projCtx, projPasswordDelta);
boolean evaluateWeak = getEvaluateWeak(projCtx);
// TODO wave
ItemDeltaItem<PrismPropertyValue<ProtectedStringType>, PrismPropertyDefinition<ProtectedStringType>> focusPasswordIdi = objectDeltaObject.findIdi(SchemaConstants.PATH_PASSWORD_VALUE);
ConfigurableValuePolicySupplier valuePolicySupplier = (result1) -> SecurityUtil.getPasswordPolicy(securityPolicy);
MappingInitializer<PrismPropertyValue<ProtectedStringType>, PrismPropertyDefinition<ProtectedStringType>> initializer = (builder) -> {
builder.mappingKind(MappingKindType.OUTBOUND).implicitSourcePath(SchemaConstants.PATH_PASSWORD_VALUE).implicitTargetPath(SchemaConstants.PATH_PASSWORD_VALUE);
builder.defaultTargetDefinition(projPasswordPropertyDefinition);
builder.defaultSource(new Source<>(focusPasswordIdi, ExpressionConstants.VAR_INPUT_QNAME));
builder.valuePolicySupplier(valuePolicySupplier);
return builder;
};
MappingOutputProcessor<PrismPropertyValue<ProtectedStringType>> processor = (mappingOutputPath, outputStruct) -> {
PrismValueDeltaSetTriple<PrismPropertyValue<ProtectedStringType>> outputTriple = outputStruct.getOutputTriple();
if (outputTriple == null) {
LOGGER.trace("Credentials 'password' expression resulted in null output triple, skipping credentials processing for {}", rsd);
return false;
}
boolean projectionIsNew = projDelta != null && (projDelta.getChangeType() == ChangeType.ADD || projCtx.getSynchronizationPolicyDecision() == SynchronizationPolicyDecision.ADD);
Collection<PrismPropertyValue<ProtectedStringType>> newValues;
if (projectionIsNew) {
newValues = outputTriple.getNonNegativeValues();
} else {
newValues = outputTriple.getPlusSet();
}
if (!canGetCleartext(newValues)) {
ObjectDelta<ShadowType> projectionPrimaryDelta = projCtx.getPrimaryDelta();
if (projectionPrimaryDelta != null) {
PropertyDelta<ProtectedStringType> passwordPrimaryDelta = projectionPrimaryDelta.findPropertyDelta(SchemaConstants.PATH_PASSWORD_VALUE);
if (passwordPrimaryDelta != null) {
// We have only hashed value coming from the mapping. There are not very useful
// for provisioning. But we have primary projection delta - and that is very likely
// to be better.
// Skip all password mappings in this case. Primary delta trumps everything.
// No weak, normal or even strong mapping can change that.
// We need to disregard even strong mapping in this case. If we would heed the strong
// mapping then account initialization won't be possible.
LOGGER.trace("We have primary password delta in projection, skipping credentials processing");
return false;
}
}
}
Collection<PrismPropertyValue<ProtectedStringType>> minusSet = outputTriple.getMinusSet();
if (!minusSet.isEmpty()) {
if (!canGetCleartext(minusSet)) {
// We have hashed values in minus set. That is not great, we won't be able to get
// cleartext from that if we need it (e.g. for runAs in provisioning).
// Therefore try to get old value from focus password delta. If that matches with
// hashed value then we have the cleartext.
ProtectedStringType oldProjectionPassword = minusSet.iterator().next().getRealValue();
PropertyDelta<ProtectedStringType> focusPasswordDelta = (PropertyDelta<ProtectedStringType>) focusPasswordIdi.getDelta();
Collection<PrismPropertyValue<ProtectedStringType>> focusPasswordDeltaOldValues = focusPasswordDelta.getEstimatedOldValues();
if (focusPasswordDeltaOldValues != null && !focusPasswordDeltaOldValues.isEmpty()) {
ProtectedStringType oldFocusPassword = requireNonNull(focusPasswordDeltaOldValues.iterator().next().getRealValue());
try {
if (oldFocusPassword.canGetCleartext() && protector.compareCleartext(oldFocusPassword, oldProjectionPassword)) {
outputTriple.clearMinusSet();
outputTriple.addToMinusSet(prismContext.itemFactory().createPropertyValue(oldFocusPassword));
}
} catch (EncryptionException e) {
throw new SystemException(e.getMessage(), e);
}
}
}
}
return true;
};
String projCtxDesc = projCtx.toHumanReadableString();
PrismObject<ShadowType> shadowNew = projCtx.getObjectNew();
MappingInitializer<PrismPropertyValue<ProtectedStringType>, PrismPropertyDefinition<ProtectedStringType>> internalInitializer = builder -> {
builder.addVariableDefinitions(ModelImplUtils.getDefaultVariablesMap(context, projCtx, true));
builder.mappingKind(MappingKindType.OUTBOUND);
builder.originType(OriginType.OUTBOUND);
builder.implicitTargetPath(SchemaConstants.PATH_PASSWORD_VALUE);
builder.originObject(projCtx.getResource());
initializer.initialize(builder);
return builder;
};
MappingEvaluatorParams<PrismPropertyValue<ProtectedStringType>, PrismPropertyDefinition<ProtectedStringType>, ShadowType, F> params = new MappingEvaluatorParams<>();
params.setMappingTypes(outboundMappingBeans);
params.setMappingDesc("password mapping" + " in projection " + projCtxDesc);
params.setNow(now);
params.setInitializer(internalInitializer);
params.setProcessor(processor);
params.setTargetLoader(new ProjectionMappingLoader<>(projCtx, contextLoader));
params.setAPrioriTargetObject(shadowNew);
params.setAPrioriTargetDelta(LensUtil.findAPrioriDelta(context, projCtx));
params.setTargetContext(projCtx);
params.setDefaultTargetItemPath(SchemaConstants.PATH_PASSWORD_VALUE);
if (context.getFocusContext() != null) {
params.setSourceContext(context.getFocusContext().getObjectDeltaObjectAbsolute());
}
params.setEvaluateCurrent(MappingTimeEval.CURRENT);
params.setEvaluateWeak(evaluateWeak);
params.setContext(context);
params.setHasFullTargetObject(projCtx.hasFullShadow());
projectionMappingSetEvaluator.evaluateMappingsToTriples(params, task, result);
}
Aggregations