Skip to content

Commit

Permalink
Merge branch 'master' of https://github.com/Evolveum/midpoint
Browse files Browse the repository at this point in the history
  • Loading branch information
KaterynaHonchar committed Apr 4, 2019
2 parents bf7cacc + b15d58f commit 5f59995
Show file tree
Hide file tree
Showing 80 changed files with 2,073 additions and 365 deletions.
4 changes: 2 additions & 2 deletions build-system/pom.xml
Expand Up @@ -684,7 +684,7 @@
<dependency>
<groupId>com.evolveum.polygon</groupId>
<artifactId>connector-ldap</artifactId>
<version>2.0</version>
<version>2.1-SNAPSHOT</version>
</dependency>
<!-- End connectors -->
<dependency>
Expand Down Expand Up @@ -1226,7 +1226,7 @@
<dependency>
<groupId>org.eclipse.jetty</groupId>
<artifactId>jetty-server</artifactId>
<version>9.4.11.v20180605</version>
<version>9.4.12.v20180830</version>
</dependency>
<dependency>
<groupId>org.apache.qpid</groupId>
Expand Down
Expand Up @@ -371,7 +371,7 @@ public boolean matches(String regex) {
* Returns true in case that there are language mutations, translation, etc.
*/
public boolean isSimple() {
return translation == null;
return translation == null && lang == null;
}

@Override
Expand Down
Expand Up @@ -474,16 +474,26 @@ public String debugDump(int indent) {
dump = null;
} else {
T realValue = value.getValue();
if (realValue instanceof ShortDumpable) {
((ShortDumpable)realValue).shortDump(sb);
} else if (realValue instanceof DebugDumpable) {

if (DebugUtil.isDetailedDebugDump() && realValue instanceof DebugDumpable) {
// Override in case that the value is both DebugDumpable and ShortDumpable
// In that case we want to force debugDump as we are in detailedDebugMode here.
// This is important e.g. for PolyString, in detailedDebugMode we want to see
// all the PolyString details.
sb.append(((DebugDumpable)realValue).debugDump(indent + 1));
} else {
if (DebugUtil.isDetailedDebugDump()) {
PrismPrettyPrinter.debugDumpValue(sb, indent + 1, realValue, prismContext, getElementName(), null);
if (realValue instanceof ShortDumpable) {
DebugUtil.indentDebugDump(sb, indent + 1);
((ShortDumpable)realValue).shortDump(sb);
} else if (realValue instanceof DebugDumpable) {
sb.append(((DebugDumpable)realValue).debugDump(indent + 1));
} else {
sb.append("SS{"+realValue+"}");
PrettyPrinter.shortDump(sb, realValue);
if (DebugUtil.isDetailedDebugDump()) {
PrismPrettyPrinter.debugDumpValue(sb, indent + 1, realValue, prismContext, getElementName(), null);
} else {
sb.append("SS{"+realValue+"}");
PrettyPrinter.shortDump(sb, realValue);
}
}
}
}
Expand Down
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2010-2018 Evolveum
* Copyright (c) 2010-2019 Evolveum
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
Expand Down Expand Up @@ -58,7 +58,9 @@ public boolean match(PolyString a, PolyString b) {
if (a == null || b == null) {
return false;
}
return MiscUtil.equals(a.getOrig(), b.getOrig()) && MiscUtil.equals(a.getNorm(), b.getNorm());
// Delegate to PolyString.equals(). This does it well. As we want to compare
// all aspects of polystring here: orig, norm, translations, langs
return a.equals(b);
}

/* (non-Javadoc)
Expand Down
Expand Up @@ -427,6 +427,9 @@ public abstract class SchemaConstants {
// be inverted, eventually (MID-356)
public static final String ICF_FRAMEWORK_URI = "http://midpoint.evolveum.com/xml/ns/public/connector/icf-1";
public static final String NS_ICF_CONFIGURATION = ICF_FRAMEWORK_URI + "/connector-schema-3";
public static final String NS_ICF_SUBTYPES = ICF_FRAMEWORK_URI + "/subtypes";
public static final QName ICF_SUBTYPES_POLYSTRING_QNAME = new QName(NS_ICF_SUBTYPES, "PolyString");
public static final String ICF_SUBTYPES_POLYSTRING_URI = QNameUtil.qNameToUri(ICF_SUBTYPES_POLYSTRING_QNAME);
public static final ItemName ICF_CONFIGURATION_PROPERTIES = new ItemName(NS_ICF_CONFIGURATION,
"configurationProperties");
public static final ItemName ICF_TIMEOUTS = new ItemName(NS_ICF_CONFIGURATION, "timeouts");
Expand Down
Expand Up @@ -15589,6 +15589,26 @@
</xsd:documentation>
</xsd:annotation>
</xsd:element>
<xsd:element name="auditSearch" type="tns:AuditSearchType" minOccurs="0" maxOccurs="1">
<xsd:annotation>
<xsd:documentation>
Specification of an explicit or implicit object collection that will be used as data source for the view.

EXTREMELY ABSOLUTELY GIGANTICALLY ENORMOUSLY MEGA GIGA TERA SUPER HYPER EXPERIMENTAL

This is almost certain to change in the future. It does not even belong here well
as this is supposed to be *object* collection and not audit collection. But for now it solves a
couple of problems in dashboards and report functionality, which is also experimental.
Therefore this is a good temporary choice.
However, if you ever rely on this element the karma will get you, eventually.
If that happens, don't come to us crying. You have been warned.
</xsd:documentation>
<xsd:appinfo>
<a:displayName>DashboardWidgetDataType.auditSearch</a:displayName>
<a:experimental>true</a:experimental>
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="baseCollection" type="tns:CollectionRefSpecificationType" minOccurs="0" maxOccurs="1">
<xsd:annotation>
<xsd:documentation>
Expand Down Expand Up @@ -16463,18 +16483,6 @@
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
<xsd:element name="auditSearch" type="tns:AuditSearchType" minOccurs="0" maxOccurs="1">
<xsd:annotation>
<xsd:documentation>
Specification of an explicit or implicit object collection that will be used as data source for the view.
EXTREMELY EXPERIMENTAL. This is almost certain to change in the future.
</xsd:documentation>
<xsd:appinfo>
<a:displayName>DashboardWidgetDataType.auditSearch</a:displayName>
<a:experimental>true</a:experimental>
</xsd:appinfo>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>

Expand Down
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2010-2017 Evolveum
* Copyright (c) 2010-2019 Evolveum
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
Expand Down Expand Up @@ -29,11 +29,13 @@
import java.util.ArrayList;
import java.util.Collection;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedHashSet;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
Expand Down Expand Up @@ -553,16 +555,36 @@ public boolean isAccountEnabled(Entry ldapEntry) {
}

public static String getAttributeValue(Entry response, String name) {
return getAttributeValue(response, name, null);
}

public static String getAttributeValue(Entry response, String name, String option) {
List<Attribute> attrs = response.getAttribute(name.toLowerCase());
if (attrs == null || attrs.size() == 0) {
Attribute attribute = findAttribute(name, option, attrs);
if (attribute == null) {
return null;
}
assertEquals("Too many attributes for name "+name+": ",
1, attrs.size());
Attribute attribute = attrs.get(0);
return getAttributeValue(attribute);
}

private static Attribute findAttribute(String name, String option, List<Attribute> attributes) {
if (attributes == null || attributes.size() == 0) {
return null;
}
for (Attribute attr : attributes) {
if (option == null) {
if (attr.getOptions() == null || attr.getOptions().isEmpty()) {
return attr;
}
} else {
if (attr.getOptions() != null && attr.getOptions().contains(option)) {
return attr;
}
}
}
return null;
}

public static String getAttributeValue(Attribute attribute) {
return attribute.iterator().next().getValue().toString();
}
Expand Down Expand Up @@ -710,6 +732,43 @@ public static void assertNoAttribute(Entry response, String name) {
}
AssertJUnit.fail("Attribute "+name+" exists while not expecting it: "+attribute);
}

public static void assertAttributeLang(Entry entry, String attributeName, String expectedOrigValue, String... params) {
List<Attribute> attrs = entry.getAttribute(attributeName.toLowerCase());
if (attrs == null || attrs.size() == 0) {
AssertJUnit.fail("Attribute "+attributeName+" does not have any value");
}
Map<String,String> expectedLangs = MiscUtil.paramsToMap(params);
List<String> langsSeen = new ArrayList<>();
for (Attribute attr : attrs) {
if (attr.size() == 0) {
throw new IllegalArgumentException("No values in attribute "+attributeName+": "+attr);
}
if (attr.size() > 1) {
throw new IllegalArgumentException("Too many values in attribute "+attributeName+": "+attr);
}
String attrValue = attr.iterator().next().toString();
if (attr.getOptions() == null || attr.getOptions().isEmpty()) {
assertEquals("Wrong orig value in attribute '"+attributeName+" in entry "+entry.getDN(), expectedOrigValue, attrValue);
} else if (attr.getOptions().size() == 1) {
String option = attr.getOptions().iterator().next();
if (!option.startsWith("lang-")) {
throw new IllegalArgumentException("Non-lang option "+option+" in attribute "+attributeName+": "+attr);
}
String lang = option.substring("lang-".length());
String expectedValue = expectedLangs.get(lang);
assertEquals("Wrong "+option+" value in attribute '"+attributeName+" in entry "+entry.getDN(), expectedValue, attrValue);
langsSeen.add(lang);
} else {
throw new IllegalArgumentException("More than one option in attribute "+attributeName+": "+attr);
}
}
for (Map.Entry<String, String> expectedLangEntry : expectedLangs.entrySet()) {
if (!langsSeen.contains(expectedLangEntry.getKey())) {
AssertJUnit.fail("No lang "+expectedLangEntry.getKey()+" in attribute "+attributeName+" in entry "+entry.getDN()+"; expected "+expectedLangEntry.getValue());
}
}
}

public void assertActive(Entry response, boolean active) {
assertEquals("Unexpected activation of entry "+response, active, isAccountEnabled(response));
Expand Down
Expand Up @@ -763,4 +763,11 @@ public static String takeThreadDump(@Nullable Thread thread) {
return dump.toString();
}

public static <K,V> Map<K, V> paramsToMap(Object[] params) {
Map<K, V> map = new HashMap<>();
for (int i=0; i < params.length; i+=2) {
map.put((K)params[i], (V)params[i+1]);
}
return map;
}
}
Expand Up @@ -17,6 +17,7 @@

import com.evolveum.midpoint.common.refinery.RefinedObjectClassDefinition;
import com.evolveum.midpoint.model.api.authentication.CompiledUserProfile;
import com.evolveum.midpoint.model.api.context.EvaluatedPolicyRule;
import com.evolveum.midpoint.model.api.context.ModelContext;
import com.evolveum.midpoint.model.api.util.MergeDeltas;
import com.evolveum.midpoint.model.api.visualizer.Scene;
Expand Down Expand Up @@ -408,4 +409,14 @@ TaskType submitTaskFromTemplate(String templateTaskOid, Map<QName, Object> exten
*/
<O extends AbstractRoleType> AssignmentCandidatesSpecification determineAssignmentHolderSpecification(PrismObject<O> assignmentTarget, OperationResult result) throws SchemaException, ConfigurationException;

/**
* Returns all policy rules that apply to the collection.
* Later, the policy rules are compiled from all the applicable sources (target, meta-roles, etc.).
* But for now we support only policy rules that are directly placed in collection assignments.
* EXPERIMENTAL. Quite likely to change later.
*/
@Experimental
@NotNull
Collection<EvaluatedPolicyRule> evaluateCollectionPolicyRules(String collectionOid, Task task, OperationResult result);

}
@@ -0,0 +1,39 @@
/**
* Copyright (c) 2019 Evolveum
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.evolveum.midpoint.model.impl.controller;

import java.util.Collection;

import org.springframework.stereotype.Component;

import com.evolveum.midpoint.model.api.context.EvaluatedPolicyRule;
import com.evolveum.midpoint.schema.result.OperationResult;
import com.evolveum.midpoint.task.api.Task;

/**
* @author semancik
*
*/
@Component
public class CollectionProcessor {

public Collection<EvaluatedPolicyRule> evaluateCollectionPolicyRules(String collectionOid, Task task,
OperationResult result) {
// TODO Work in progress
return null;
}

}
Expand Up @@ -67,6 +67,7 @@
import com.evolveum.midpoint.model.api.authentication.UserProfileService;
import com.evolveum.midpoint.model.api.context.EvaluatedAssignment;
import com.evolveum.midpoint.model.api.context.EvaluatedAssignmentTarget;
import com.evolveum.midpoint.model.api.context.EvaluatedPolicyRule;
import com.evolveum.midpoint.model.api.context.ModelContext;
import com.evolveum.midpoint.model.api.hooks.ChangeHook;
import com.evolveum.midpoint.model.api.hooks.HookRegistry;
Expand Down Expand Up @@ -196,6 +197,7 @@ public class ModelInteractionServiceImpl implements ModelInteractionService {
@Autowired private ExpressionFactory expressionFactory;
@Autowired private OperationalDataManager metadataManager;
@Autowired private Clockwork clockwork;
@Autowired private CollectionProcessor collectionProcessor;

private static final String OPERATION_GENERATE_VALUE = ModelInteractionService.class.getName() + ".generateValue";
private static final String OPERATION_VALIDATE_VALUE = ModelInteractionService.class.getName() + ".validateValue";
Expand Down Expand Up @@ -1910,4 +1912,9 @@ private <O extends ObjectType> ArchetypePolicyType getArchetypePolicyLegacy(Pris
return objectPolicyConfiguration;
}

@Override
public Collection<EvaluatedPolicyRule> evaluateCollectionPolicyRules(String collectionOid, Task task, OperationResult result) {
return collectionProcessor.evaluateCollectionPolicyRules(collectionOid, task, result);
}

}
Expand Up @@ -989,6 +989,10 @@ public void testConnectionConnector(ConnectorSpec connectorSpec, Map<String,Coll
modifyResourceAvailabilityStatus(connectorSpec.getResource(), AvailabilityStatusType.BROKEN, parentResult);
capabilitiesResult.recordFatalError("Configuration error", e);
return;
} catch (SchemaException e) {
modifyResourceAvailabilityStatus(connectorSpec.getResource(), AvailabilityStatusType.BROKEN, parentResult);
capabilitiesResult.recordFatalError("Schema error", e);
return;
} catch (RuntimeException | Error e) {
modifyResourceAvailabilityStatus(connectorSpec.getResource(), AvailabilityStatusType.BROKEN, parentResult);
capabilitiesResult.recordFatalError("Unexpected runtime error", e);
Expand Down
Expand Up @@ -69,7 +69,17 @@ public abstract class AbstractOpenDjTest extends AbstractIntegrationTest {
protected static final File ACCOUNT_WILL_FILE = new File(TEST_DIR, "account-will.xml");
protected static final String ACCOUNT_WILL_OID = "c0c010c0-d34d-b44f-f11d-333222123456";
protected static final String ACCOUNT_WILL_DN = "uid=will,ou=People,dc=example,dc=com";


protected static final File ACCOUNT_POLY_FILE = new File(TEST_DIR, "account-poly.xml");
protected static final String ACCOUNT_POLY_OID = "cef31578-5493-11e9-bbed-17f032005a6b";
protected static final String ACCOUNT_POLY_DN = "uid=poly,ou=People,dc=example,dc=com";
protected static final String ACCOUNT_POLY_DESCRIPTION_ORIG = "Poly the Parrot";
protected static final String ACCOUNT_POLY_DESCRIPTION_EN = "Polly the Parrot";
protected static final String ACCOUNT_POLY_DESCRIPTION_SK = "Papagáj Poly";
protected static final String ACCOUNT_POLY_DESCRIPTION_CZ = "Papoušek Poly";
protected static final String ACCOUNT_POLY_DESCRIPTION_HR = "Papiga Poly";
protected static final String ACCOUNT_POLY_DESCRIPTION_RU = "Попугай Поли";

protected static final File ACCOUNT_BAD_FILE = new File(TEST_DIR, "account-bad.xml");
protected static final String ACCOUNT_BAD_OID = "dbb0c37d-9ee6-44a4-8d39-016dbce1ffff";

Expand Down Expand Up @@ -140,6 +150,8 @@ public abstract class AbstractOpenDjTest extends AbstractIntegrationTest {
public static final QName RESOURCE_OPENDJ_ACCOUNT_OBJECTCLASS = new QName(RESOURCE_NS, "inetOrgPerson");
public static final QName RESOURCE_OPENDJ_GROUP_OBJECTCLASS = new QName(RESOURCE_NS, "groupOfUniqueNames");
public static final QName RESOURCE_OPENDJ_POSIX_ACCOUNT_OBJECTCLASS = new QName(RESOURCE_NS, "posixAccount");
public static final String ATTRIBUTE_DESCRIPTION_NAME = "description";
public static final ItemName ATTRIBUTE_DESCRIPTION_QNAME = new ItemName(RESOURCE_OPENDJ_NS, ATTRIBUTE_DESCRIPTION_NAME);

protected static final File QUERY_COMPLEX_FILTER_FILE = new File(TEST_DIR, "query-complex-filter.xml");
protected static final File QUERY_ALL_ACCOUNTS_FILE = new File(TEST_DIR, "query-filter-all-accounts.xml");
Expand Down

0 comments on commit 5f59995

Please sign in to comment.