From 2033b81b8d2121cb4ca81fa3b547ae31e27d57f3 Mon Sep 17 00:00:00 2001
From: Katarina Valalikova
Date: Mon, 8 Jun 2020 17:46:11 +0200
Subject: [PATCH] adding possibility to define object selector for
autoassignments (MID-5497, MID-5734)
---
.../xml/ns/public/common/common-core-3.xsd | 13 +-
.../focus/ObjectTemplateProcessor.java | 47 +++---
.../model/intest/rbac/TestAutoassign.java | 149 ++++++++++++++++--
.../rbac/autoassign/role-unit-rider.xml | 48 ++++++
.../rbac/autoassign/role-unit-sleeper.xml | 3 +
.../rbac/autoassign/role-unit-walker.xml | 3 +
.../rbac/autoassign/role-unit-worker.xml | 3 +
7 files changed, 226 insertions(+), 40 deletions(-)
create mode 100644 model/model-intest/src/test/resources/rbac/autoassign/role-unit-rider.xml
diff --git a/infra/schema/src/main/resources/xml/ns/public/common/common-core-3.xsd b/infra/schema/src/main/resources/xml/ns/public/common/common-core-3.xsd
index baec7735e0d..1e6140b320c 100755
--- a/infra/schema/src/main/resources/xml/ns/public/common/common-core-3.xsd
+++ b/infra/schema/src/main/resources/xml/ns/public/common/common-core-3.xsd
@@ -13116,7 +13116,7 @@
(abstract) role.
- Use with care. MidPoint will will have to process all the roles that
+ Use with care. MidPoint will have to process all the roles that
have this flag set to true. All the roles will be looked up, autoassign
specification will be processed to see if the focus is matching.
This will happen all the time for all modification operations.
@@ -13181,6 +13181,15 @@
+
+
+
+
+ Restrics autoassignment to concrete focus type.
+
+
+
+
@@ -13621,7 +13630,7 @@
-
+
Selects some objects from all the objects in midPoint.
diff --git a/model/model-impl/src/main/java/com/evolveum/midpoint/model/impl/lens/projector/focus/ObjectTemplateProcessor.java b/model/model-impl/src/main/java/com/evolveum/midpoint/model/impl/lens/projector/focus/ObjectTemplateProcessor.java
index 316ccc949c6..91bcaa88589 100644
--- a/model/model-impl/src/main/java/com/evolveum/midpoint/model/impl/lens/projector/focus/ObjectTemplateProcessor.java
+++ b/model/model-impl/src/main/java/com/evolveum/midpoint/model/impl/lens/projector/focus/ObjectTemplateProcessor.java
@@ -24,6 +24,11 @@
import com.evolveum.midpoint.prism.delta.*;
import com.evolveum.midpoint.prism.equivalence.EquivalenceStrategy;
import com.evolveum.midpoint.prism.path.ItemPathCollectionsUtil;
+import com.evolveum.midpoint.schema.ObjectSelector;
+import com.evolveum.midpoint.util.QNameUtil;
+import com.evolveum.midpoint.util.exception.*;
+import com.evolveum.midpoint.xml.ns._public.common.common_3.*;
+
import org.apache.commons.lang.BooleanUtils;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -57,32 +62,8 @@
import com.evolveum.midpoint.schema.result.OperationResult;
import com.evolveum.midpoint.task.api.Task;
import com.evolveum.midpoint.util.DebugUtil;
-import com.evolveum.midpoint.util.exception.CommunicationException;
-import com.evolveum.midpoint.util.exception.ConfigurationException;
-import com.evolveum.midpoint.util.exception.ExpressionEvaluationException;
-import com.evolveum.midpoint.util.exception.ObjectNotFoundException;
-import com.evolveum.midpoint.util.exception.PolicyViolationException;
-import com.evolveum.midpoint.util.exception.SchemaException;
-import com.evolveum.midpoint.util.exception.SecurityViolationException;
import com.evolveum.midpoint.util.logging.Trace;
import com.evolveum.midpoint.util.logging.TraceManager;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.AbstractRoleType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.AssignmentHolderType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.AutoassignMappingType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.AutoassignSpecificationType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.FocalAutoassignSpecificationType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.FocusType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.MappingStrengthType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.MappingType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.ObjectReferenceType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.ObjectTemplateItemDefinitionType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.ObjectTemplateMappingEvaluationPhaseType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.ObjectTemplateMappingType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.ObjectTemplateType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.ObjectType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.RoleManagementConfigurationType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.SystemConfigurationType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.VariableBindingDefinitionType;
import com.evolveum.prism.xml.ns._public.types_3.ItemPathType;
import static com.evolveum.midpoint.model.impl.lens.projector.util.SkipWhenFocusDeleted.PRIMARY;
@@ -459,6 +440,11 @@ private void collectAutoassignMappings(LensCon
if (focalAutoassignSpec == null) {
return true;
}
+
+ if (!isApplicableFor(focalAutoassignSpec.getSelector(), context.getFocusContext(), objectResult)) {
+ return true;
+ }
+
for (AutoassignMappingType autoMapping: focalAutoassignSpec.getMapping()) {
AutoassignMappingType mapping = autoMapping.clone();
setMappingTarget(mapping, new ItemPathType(SchemaConstants.PATH_ASSIGNMENT));
@@ -470,6 +456,19 @@ private void collectAutoassignMappings(LensCon
cacheRepositoryService.searchObjectsIterative(AbstractRoleType.class, query, handler, GetOperationOptions.createReadOnlyCollection(), true, result);
}
+ private boolean isApplicableFor(ObjectSelectorType selector, LensFocusContext focusContext, OperationResult result) {
+ if (selector == null) {
+ return true;
+ }
+ try {
+ return cacheRepositoryService.selectorMatches(selector, focusContext.getObjectAny(), null, LOGGER, "");
+ } catch (SchemaException | SecurityViolationException | ExpressionEvaluationException | CommunicationException | ObjectNotFoundException | ConfigurationException e) {
+ LOGGER.error("Failed to evaluate selector constraints, selector {}, focusContext {}\nReason: {}", selector, focusContext, e.getMessage(), e);
+ result.recordFatalError("Failed to evaluate selector constrains, selector: " + selector + ", focusContext: " + focusContext + "\nReason: " + e.getMessage(), e);
+ throw new SystemException(e);
+ }
+ }
+
private void setMappingTarget(MappingType mapping, ItemPathType path) {
VariableBindingDefinitionType target = mapping.getTarget();
if (target == null) {
diff --git a/model/model-intest/src/test/java/com/evolveum/midpoint/model/intest/rbac/TestAutoassign.java b/model/model-intest/src/test/java/com/evolveum/midpoint/model/intest/rbac/TestAutoassign.java
index 08232a4986f..a772a2bfaae 100644
--- a/model/model-intest/src/test/java/com/evolveum/midpoint/model/intest/rbac/TestAutoassign.java
+++ b/model/model-intest/src/test/java/com/evolveum/midpoint/model/intest/rbac/TestAutoassign.java
@@ -10,6 +10,10 @@
import javax.xml.datatype.XMLGregorianCalendar;
+import com.evolveum.midpoint.prism.path.ItemPath;
+
+import com.evolveum.midpoint.xml.ns._public.common.common_3.*;
+
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.annotation.DirtiesContext.ClassMode;
import org.springframework.test.context.ContextConfiguration;
@@ -20,11 +24,6 @@
import com.evolveum.midpoint.schema.result.OperationResult;
import com.evolveum.midpoint.task.api.Task;
import com.evolveum.midpoint.test.DummyResourceContoller;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.RoleManagementConfigurationType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.RoleType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.SystemConfigurationType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.SystemObjectsType;
-import com.evolveum.midpoint.xml.ns._public.common.common_3.UserType;
/**
* @author semancik
@@ -47,9 +46,14 @@ public class TestAutoassign extends AbstractRbacTest {
protected static final String ROLE_UNIT_WALKER_OID = "a2bc45fc-bfec-11e7-bdfd-af4b3e689502";
protected static final String ROLE_UNIT_WALKER_TITLE = "Walker";
+ protected static final File ROLE_UNIT_RIDER_FILE = new File(AUTOASSIGN_DIR, "role-unit-rider.xml");
+ protected static final String ROLE_UNIT_RIDER_OID = "9a60cdc6-f2ad-4414-964b-5fd1dfaec157";
+ protected static final String ROLE_UNIT_RIDER_TITLE = "Rider";
+
protected static final String UNIT_WORKER = "worker";
protected static final String UNIT_SLEEPER = "sleeper";
protected static final String UNIT_WALKER = "walker";
+ protected static final String UNIT_RIDER = "rider";
private static final XMLGregorianCalendar ROLE_SLEEPER_AUTOASSIGN_VALID_TO =
XmlTypeConverter.createXMLGregorianCalendar(2222, 1, 2, 3, 4, 5);
@@ -62,16 +66,13 @@ public void initSystem(Task initTask, OperationResult initResult)
repoAddObjectFromFile(ROLE_UNIT_WORKER_FILE, RoleType.class, initResult);
repoAddObjectFromFile(ROLE_UNIT_SLEEPER_FILE, RoleType.class, initResult);
repoAddObjectFromFile(ROLE_UNIT_WALKER_FILE, RoleType.class, initResult);
+ repoAddObjectFromFile(ROLE_UNIT_RIDER_FILE, RoleType.class, initResult);
+
+ repoAddObjectFromFile(ARCHETYPE_EMPLOYEE_FILE, ArchetypeType.class, initResult);
- // Temporarily using repository service because of MID-5497
- repositoryService.modifyObject(SystemConfigurationType.class, SystemObjectsType.SYSTEM_CONFIGURATION.value(),
- prismContext.deltaFor(SystemConfigurationType.class)
- .item(SystemConfigurationType.F_ROLE_MANAGEMENT, RoleManagementConfigurationType.F_AUTOASSIGN_ENABLED)
- .replace(true)
- .asItemDeltas(), initResult);
-// modifyObjectReplaceProperty(SystemConfigurationType.class, SystemObjectsType.SYSTEM_CONFIGURATION.value(),
-// ItemPath.create(SystemConfigurationType.F_ROLE_MANAGEMENT, RoleManagementConfigurationType.F_AUTOASSIGN_ENABLED),
-// initTask, initResult, Boolean.TRUE);
+ modifyObjectReplaceProperty(SystemConfigurationType.class, SystemObjectsType.SYSTEM_CONFIGURATION.value(),
+ ItemPath.create(SystemConfigurationType.F_ROLE_MANAGEMENT, RoleManagementConfigurationType.F_AUTOASSIGN_ENABLED),
+ initTask, initResult, Boolean.TRUE);
}
/**
@@ -239,6 +240,126 @@ public void test114ModifyUnitAddSleeper() throws Exception {
ROLE_UNIT_WORKER_TITLE, ROLE_UNIT_WALKER_TITLE, ROLE_UNIT_SLEEPER_TITLE);
}
+ @Test
+ public void test115ModifyUnitAddRider() throws Exception {
+ // GIVEN
+ Task task = getTestTask();
+ OperationResult result = task.getResult();
+
+ // WHEN
+ modifyUserAdd(USER_JACK_OID, UserType.F_ORGANIZATIONAL_UNIT, task, result,
+ createPolyString(UNIT_RIDER));
+
+ // THEN
+ assertSuccess(result);
+
+ assertUserAfter(USER_JACK_OID)
+ .assertOrganizationalUnits(UNIT_WORKER, UNIT_WALKER, UNIT_SLEEPER, UNIT_RIDER)
+ .assignments()
+ .assertAssignments(3)
+ .assertRole(ROLE_UNIT_WORKER_OID)
+ .assertRole(ROLE_UNIT_WALKER_OID)
+ .assertRole(ROLE_UNIT_SLEEPER_OID)
+ .assertNoRole(ROLE_UNIT_RIDER_OID)
+ .end()
+ .links()
+ .single();
+
+ assertDummyAccountByUsername(null, USER_JACK_USERNAME)
+ .assertAttribute(DummyResourceContoller.DUMMY_ACCOUNT_ATTRIBUTE_TITLE_NAME,
+ ROLE_UNIT_WORKER_TITLE, ROLE_UNIT_WALKER_TITLE, ROLE_UNIT_SLEEPER_TITLE);
+ }
+
+ /**
+ * Prepare user guybrush for autoassignment
+ */
+ @Test
+ public void test200assignArchetypeGuybrush() throws Exception {
+ // GIVEN
+ Task task = getTestTask();
+ OperationResult result = task.getResult();
+
+ //WHEN
+ assignArchetype(USER_GUYBRUSH_OID, ARCHETYPE_EMPLOYEE_OID, task, result);
+
+ //THEN
+ assertUserAfter(USER_GUYBRUSH_OID)
+ .assertArchetypeRef(ARCHETYPE_EMPLOYEE_OID)
+ .assignments()
+ .assertAssignments(1)
+ .assertArchetype(ARCHETYPE_EMPLOYEE_OID)
+ .end();
+
+ }
+
+ @Test
+ public void test201addUnitRiderGuybrush() throws Exception {
+ //GIVEN
+ Task task = getTestTask();
+ OperationResult result = task.getResult();
+
+ //WHEN
+ modifyUserAdd(USER_GUYBRUSH_OID, UserType.F_ORGANIZATIONAL_UNIT, task, result, createPolyString(UNIT_RIDER));
+
+ //THEN
+ assertUserAfter(USER_GUYBRUSH_OID)
+ .assertOrganizationalUnits(UNIT_RIDER)
+ .assertArchetypeRef(ARCHETYPE_EMPLOYEE_OID)
+ .assignments()
+ .assertAssignments(2)
+ .assertArchetype(ARCHETYPE_EMPLOYEE_OID)
+ .assertRole(ROLE_UNIT_RIDER_OID)
+ .end()
+ .links()
+ .single();
+ }
+
+ @Test
+ public void test202addUnitSleeperGuybrush() throws Exception {
+ //GIVEN
+ Task task = getTestTask();
+ OperationResult result = task.getResult();
+
+ //WHEN
+ modifyUserAdd(USER_GUYBRUSH_OID, UserType.F_ORGANIZATIONAL_UNIT, task, result, createPolyString(UNIT_SLEEPER));
+
+ //THEN
+ assertUserAfter(USER_GUYBRUSH_OID)
+ .assertOrganizationalUnits(UNIT_RIDER, UNIT_SLEEPER)
+ .assertArchetypeRef(ARCHETYPE_EMPLOYEE_OID)
+ .assignments()
+ .assertAssignments(3)
+ .assertArchetype(ARCHETYPE_EMPLOYEE_OID)
+ .assertRole(ROLE_UNIT_RIDER_OID)
+ .assertRole(ROLE_UNIT_SLEEPER_OID)
+ .end()
+ .links()
+ .single();
+ }
+
+ @Test
+ public void test203removeUnitRiderGuybrush() throws Exception {
+ //GIVEN
+ Task task = getTestTask();
+ OperationResult result = task.getResult();
+
+ //WHEN
+ modifyUserDelete(USER_GUYBRUSH_OID, UserType.F_ORGANIZATIONAL_UNIT, task, result, createPolyString(UNIT_RIDER));
+
+ //THEN
+ assertUserAfter(USER_GUYBRUSH_OID)
+ .assertArchetypeRef(ARCHETYPE_EMPLOYEE_OID)
+ .assignments()
+ .assertAssignments(2)
+ .assertArchetype(ARCHETYPE_EMPLOYEE_OID)
+ .assertNoRole(ROLE_UNIT_RIDER_OID)
+ .assertRole(ROLE_UNIT_SLEEPER_OID)
+ .end()
+ .links()
+ .single();
+ }
+
+
// TODO: org and relation
// TODO: combine autoassign with object template role assign
diff --git a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-rider.xml b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-rider.xml
new file mode 100644
index 00000000000..a25c84fe6ee
--- /dev/null
+++ b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-rider.xml
@@ -0,0 +1,48 @@
+
+
+ Unit Rider
+
+
+
+ account
+
+ [ri:title]
+
+
+ Rider
+
+
+
+
+
+
+ true
+
+
+ UserType
+
+
+
+ autoassign-rider
+ true
+
+ organizationalUnit
+
+
+
+
+
+
+
+
diff --git a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-sleeper.xml b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-sleeper.xml
index bb2f8d1b9f5..51784033504 100644
--- a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-sleeper.xml
+++ b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-sleeper.xml
@@ -27,6 +27,9 @@
true
+
+ UserType
+
autoassign-sleeper
true
diff --git a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-walker.xml b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-walker.xml
index fac2063254c..56d4bbb0878 100644
--- a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-walker.xml
+++ b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-walker.xml
@@ -27,6 +27,9 @@
true
+
+ UserType
+
autoassign-walker
true
diff --git a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-worker.xml b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-worker.xml
index c0befb16a17..9f079d52252 100644
--- a/model/model-intest/src/test/resources/rbac/autoassign/role-unit-worker.xml
+++ b/model/model-intest/src/test/resources/rbac/autoassign/role-unit-worker.xml
@@ -27,6 +27,9 @@
true
+
+ UserType
+
autoassign-worker
true