Skip to content

Commit

Permalink
MID-8093 options to customize search result in target selection step …
Browse files Browse the repository at this point in the history
…in request access wizard.
  • Loading branch information
1azyman committed Sep 13, 2022
1 parent f5d2ec9 commit 819bc47
Show file tree
Hide file tree
Showing 2 changed files with 119 additions and 5 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@
import java.util.stream.Collectors;
import javax.xml.namespace.QName;

import com.evolveum.midpoint.util.logging.LoggingUtils;

import org.apache.commons.lang3.BooleanUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.wicket.ajax.AjaxRequestTarget;
Expand All @@ -33,17 +35,30 @@
import com.evolveum.midpoint.gui.api.component.wizard.WizardModel;
import com.evolveum.midpoint.gui.api.model.LoadableModel;
import com.evolveum.midpoint.gui.api.page.PageBase;
import com.evolveum.midpoint.gui.api.util.ModelServiceLocator;
import com.evolveum.midpoint.gui.api.util.WebComponentUtil;
import com.evolveum.midpoint.gui.api.util.WebModelServiceUtils;
import com.evolveum.midpoint.gui.impl.component.tile.Tile;
import com.evolveum.midpoint.gui.impl.component.tile.TilePanel;
import com.evolveum.midpoint.prism.PrismContext;
import com.evolveum.midpoint.prism.PrismObject;
import com.evolveum.midpoint.prism.PrismPropertyDefinition;
import com.evolveum.midpoint.prism.PrismPropertyValue;
import com.evolveum.midpoint.prism.delta.PrismValueDeltaSetTriple;
import com.evolveum.midpoint.prism.query.ObjectFilter;
import com.evolveum.midpoint.prism.query.ObjectQuery;
import com.evolveum.midpoint.repo.common.expression.Expression;
import com.evolveum.midpoint.repo.common.expression.ExpressionEvaluationContext;
import com.evolveum.midpoint.repo.common.expression.ExpressionFactory;
import com.evolveum.midpoint.schema.constants.ExpressionConstants;
import com.evolveum.midpoint.schema.expression.VariablesMap;
import com.evolveum.midpoint.schema.result.OperationResult;
import com.evolveum.midpoint.schema.util.MiscSchemaUtil;
import com.evolveum.midpoint.security.api.MidPointPrincipal;
import com.evolveum.midpoint.security.api.SecurityUtil;
import com.evolveum.midpoint.task.api.Task;
import com.evolveum.midpoint.util.DOMUtil;
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;
Expand Down Expand Up @@ -323,8 +338,17 @@ public void setObject(Collection<ObjectReferenceType> object) {

Select2MultiChoice<ObjectReferenceType> multiselect = new Select2MultiChoice<>(ID_MULTISELECT, multiselectModel,
new ObjectReferenceProvider(this));

GroupSelectionType group = getSelectedGroupSelection();
int minLength = 2;
if (group != null && group.getAutocompleteMinChars() != null) {
minLength = group.getAutocompleteMinChars();
}
if (minLength < 0) {
minLength = 2;
}
multiselect.getSettings()
.setMinimumInputLength(2);
.setMinimumInputLength(minLength);
multiselect.add(new AjaxFormComponentUpdatingBehavior("change") {

@Override
Expand Down Expand Up @@ -451,15 +475,27 @@ private void groupOthersPerformed(AjaxRequestTarget target, Tile<PersonOfInteres
target.add(this);
}

private ObjectFilter createObjectFilterFromGroupSelection(String identifier) {
if (identifier == null) {
private GroupSelectionType getSelectedGroupSelection() {
Tile<PersonOfInterest> selected = getSelectedTile();
if (selected == null) {
return null;
}

TargetSelectionType targetSelection = getTargetSelectionConfiguration();
String identifier = selected.getValue().groupIdentifier;
if (identifier == null) {
return null;
}

List<GroupSelectionType> selections = getTargetSelectionConfiguration().getGroup();
GroupSelectionType selection = selections.stream().filter(gs -> identifier.equals(gs.getIdentifier())).findFirst().orElse(null);
return selections.stream().filter(gs -> identifier.equals(gs.getIdentifier())).findFirst().orElse(null);
}

private ObjectFilter createObjectFilterFromGroupSelection(String identifier) {
if (identifier == null) {
return null;
}

GroupSelectionType selection = getSelectedGroupSelection();
if (selection == null) {
return null;
}
Expand Down Expand Up @@ -701,12 +737,73 @@ private String getDisplayName(PrismObject<UserType> o) {
return null;
}

String identifier = null;
Tile<PersonOfInterest> selected = panel.getSelectedTile();
if (selected != null) {
identifier = selected.getValue().groupIdentifier;
}

if (identifier == null) {
return getDefaultUserDisplayName(o);
}

GroupSelectionType group = panel.getSelectedGroupSelection();
if (group == null || group.getUserDisplayName() == null) {
return getDefaultUserDisplayName(o);
}

String displayName = getUserDisplayNameFromExpression(identifier, group.getUserDisplayName(), o);

return StringUtils.isNotEmpty(displayName) ? displayName : getDefaultUserDisplayName(o);
}

private String getDefaultUserDisplayName(PrismObject<UserType> o) {
String name = WebComponentUtil.getOrigStringFromPoly(o.getName());
String fullName = WebComponentUtil.getOrigStringFromPoly(o.asObjectable().getFullName());

return StringUtils.isNotEmpty(fullName) ? fullName + " (" + name + ")" : name;
}

private String getUserDisplayNameFromExpression(String identifier, ExpressionType expressionType, PrismObject<UserType> object) {
String contextDesc = "User display name for group selection '" + identifier + "' expression";

ModelServiceLocator locator = panel.page;

Task task = panel.page.getPageTask();
OperationResult result = task.getResult();

try {
ExpressionFactory factory = locator.getExpressionFactory();
PrismContext ctx = object.getPrismContext();
PrismPropertyDefinition<String> outputDefinition = ctx.definitionFactory().createPropertyDefinition(ExpressionConstants.OUTPUT_ELEMENT_NAME,
DOMUtil.XSD_STRING);
Expression<PrismPropertyValue<String>, PrismPropertyDefinition<String>> expression =
factory.makeExpression(expressionType, outputDefinition, MiscSchemaUtil.getExpressionProfile(), contextDesc, task, result);

VariablesMap variables = new VariablesMap();
variables.put(ExpressionConstants.VAR_OBJECT, object, object.getDefinition());

ExpressionEvaluationContext context = new ExpressionEvaluationContext(null, variables, contextDesc, task);
PrismValueDeltaSetTriple<PrismPropertyValue<String>> outputTriple = expression.evaluate(context, result);
if (outputTriple == null) {
return null;
}
Collection<PrismPropertyValue<String>> outputValues = outputTriple.getNonNegativeValues();
if (outputValues.isEmpty()) {
return null;
}
if (outputValues.size() > 1) {
return null;
}
return outputValues.iterator().next().getRealValue();
} catch (Exception ex) {
result.recordFatalError(ex);
LoggingUtils.logUnexpectedException(LOGGER, contextDesc, ex);
}

return null;
}

@Override
public Collection<ObjectReferenceType> toChoices(Collection<String> collection) {
return collection.stream()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -357,6 +357,23 @@
<xsd:element name="identifier" type="xsd:string"/>
<xsd:element name="display" type="tns:DisplayType"/>
<xsd:element name="collection" type="tns:CollectionRefSpecificationType"/>
<xsd:element name="searchFilterTemplate" type="q:SearchFilterType" minOccurs="0"/>
<xsd:element name="userDisplayName" type="tns:ExpressionType" minOccurs="0">
<xsd:annotation>
<xsd:documentation>
Expression that can be used to return String value which describes user object returned by search.
By default `user.getFullName() + "(" + user.getName() + ")"` is used.
</xsd:documentation>
</xsd:annotation>
</xsd:element>
<xsd:element name="autocompleteMinChars" type="xsd:int" minOccurs="0">
<xsd:annotation>
<xsd:documentation>
Minimum number of characters that needs to be typed into autocomplete widget before search will start.
Default value: 2
</xsd:documentation>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
<xsd:attribute name="id" type="xsd:long"/>
</xsd:complexType>
Expand Down

0 comments on commit 819bc47

Please sign in to comment.