chemistry-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From j...@apache.org
Subject svn commit: r1454478 - in /chemistry/opencmis/trunk/chemistry-opencmis-server: chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/ chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmi...
Date Fri, 08 Mar 2013 17:40:35 GMT
Author: jens
Date: Fri Mar  8 17:40:34 2013
New Revision: 1454478

URL: http://svn.apache.org/r1454478
Log:
TypeValidator: check for unknown properties when using secondary types

Modified:
    chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryAbstractServiceImpl.java
    chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryObjectServiceImpl.java
    chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/TypeValidationTest.java
    chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-support/src/main/java/org/apache/chemistry/opencmis/server/support/TypeValidator.java

Modified: chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryAbstractServiceImpl.java
URL: http://svn.apache.org/viewvc/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryAbstractServiceImpl.java?rev=1454478&r1=1454477&r2=1454478&view=diff
==============================================================================
--- chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryAbstractServiceImpl.java
(original)
+++ chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryAbstractServiceImpl.java
Fri Mar  8 17:40:34 2013
@@ -18,6 +18,9 @@
  */
 package org.apache.chemistry.opencmis.inmemory.server;
 
+import java.util.ArrayList;
+import java.util.List;
+
 import org.apache.chemistry.opencmis.commons.PropertyIds;
 import org.apache.chemistry.opencmis.commons.data.Properties;
 import org.apache.chemistry.opencmis.commons.definitions.TypeDefinition;
@@ -65,6 +68,22 @@ public class InMemoryAbstractServiceImpl
         return typeDefC.getTypeDefinition();
     }
 
+    protected List<TypeDefinition> getTypeDefinition(String repositoryId, List<String>
typeIds) {
+        if (null == typeIds || typeIds.isEmpty())
+            return null;
+        
+        List<TypeDefinition> result = new ArrayList<TypeDefinition>(typeIds.size());
+        for (String typeId : typeIds) {
+            TypeDefinitionContainer typeDefC = fStoreManager.getTypeById(repositoryId, typeId);
+            if (typeDefC == null) {
+                throw new CmisInvalidArgumentException("Cannot create object, a type with
id " + typeId + " is unknown");
+            }
+            result.add(typeDefC.getTypeDefinition());
+        }
+
+        return result;
+    }
+
     protected TypeDefinition getTypeDefinition(String repositoryId, StoredObject obj) {
 
         TypeDefinitionContainer typeDefC = fStoreManager.getTypeById(repositoryId, obj.getTypeId());

Modified: chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryObjectServiceImpl.java
URL: http://svn.apache.org/viewvc/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryObjectServiceImpl.java?rev=1454478&r1=1454477&r2=1454478&view=diff
==============================================================================
--- chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryObjectServiceImpl.java
(original)
+++ chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/main/java/org/apache/chemistry/opencmis/inmemory/server/InMemoryObjectServiceImpl.java
Fri Mar  8 17:40:34 2013
@@ -20,6 +20,7 @@ package org.apache.chemistry.opencmis.in
 
 import java.math.BigInteger;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collections;
 import java.util.HashMap;
 import java.util.HashSet;
@@ -1242,30 +1243,28 @@ public class InMemoryObjectServiceImpl e
             typeDef = getTypeDefinition(repositoryId, properties);
             
         // check properties for validity
-        TypeValidator.validateProperties(typeDef, properties, cmis11, checkMandatory, cmis11);
-        
-        if (!cmis11)
+        if (!cmis11) {
+            TypeValidator.validateProperties(typeDef, properties, checkMandatory, cmis11);
             return;
+        }
         
         // CMIS 1.1 secondary types
         PropertyData<?> pd = properties.getProperties().get(PropertyIds.SECONDARY_OBJECT_TYPE_IDS);
         
         @SuppressWarnings("unchecked")
         List<String> secondaryTypeIds = (List<String>) (pd == null ? null : pd.getValues());
+        // if no secondary types are passed use the existing ones:
         if (null != so && (null == secondaryTypeIds || secondaryTypeIds.size() ==
0)) {
             secondaryTypeIds = so.getSecondaryTypeIds();
         }
         
         if (null != secondaryTypeIds && secondaryTypeIds.size() != 0) {
-            // check if they are all valid
-            for (String typeId : secondaryTypeIds) {
-                TypeDefinitionContainer typeDefC = fStoreManager.getTypeById(repositoryId,
typeId);
-                typeDef =  typeDefC == null ? null : typeDefC.getTypeDefinition();
-                if (null == typeDef) {
-                    throw new CmisInvalidArgumentException("Cannot set secondary type, a
type with id " + typeId + " is unknown");                    
-                }
-                TypeValidator.validateProperties(typeDef, properties, true, checkMandatory,
true);
-            }
+            List<String> allTypeIds = new ArrayList<String>(secondaryTypeIds);
+            allTypeIds.add(typeDef.getId());
+            List<TypeDefinition> typeDefs = getTypeDefinition(repositoryId, allTypeIds);
+            TypeValidator.validateProperties(typeDefs, properties, checkMandatory);
+        } else {
+            TypeValidator.validateProperties(typeDef, properties, checkMandatory, true);
         }
     }
     

Modified: chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/TypeValidationTest.java
URL: http://svn.apache.org/viewvc/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/TypeValidationTest.java?rev=1454478&r1=1454477&r2=1454478&view=diff
==============================================================================
--- chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/TypeValidationTest.java
(original)
+++ chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-inmemory/src/test/java/org/apache/chemistry/opencmis/inmemory/TypeValidationTest.java
Fri Mar  8 17:40:34 2013
@@ -21,6 +21,7 @@ package org.apache.chemistry.opencmis.in
 import java.math.BigDecimal;
 import java.math.BigInteger;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collections;
 import java.util.HashMap;
 import java.util.List;
@@ -399,6 +400,64 @@ public class TypeValidationTest extends 
         }
     }
 
+    @Test
+    public void testAllPropertiesKnown() {
+
+        String unknownPropertyId = "UnknownProperty";
+        List<PropertyData<?>> properties = createPropertiesWithNameAndTypeId(MY_DOC_TYPE);
+        properties.add(FACTORY.createPropertyBooleanData("BooleanProp", true));
+        // add unknown property
+        properties.add(FACTORY.createPropertyStringData(unknownPropertyId, "SomeValue"));
+        Properties props = FACTORY.createPropertiesData(properties);
+
+        // validate properties according to type
+        TypeDefinition typeDef = buildMyType();
+
+        try {
+            TypeValidator.validateProperties(typeDef, props, true);
+            fail("TypeValidator should throw CMISConstraintException if property is not known
in type.");
+        } catch (CmisConstraintException e) {
+            assertTrue(e.getMessage().contains("Unknown property"));
+            assertTrue(e.getMessage().contains(unknownPropertyId));
+        }
+    }
+
+    @Test
+    public void testAllPropertiesKnownSecondaryTypes() {
+
+        TypeDefinition primaryType = buildTypeWithStringProp();
+        TypeDefinition secondaryType1 = buildTypeWithIntegerProp();
+        TypeDefinition secondaryType2 = buildTypeWithDecimalProp();
+        
+        String unknownPropertyId = "UnknownProperty";
+        List<PropertyData<?>> properties = createPropertiesWithSecondaryTypes(MY_DOC_TYPE,
Arrays.asList(INT_DOC_TYPE, DECIMAL_DOC_TYPE));
+        
+        // add unknown property
+        properties.add(FACTORY.createPropertyStringData(unknownPropertyId, "SomeValue"));
+        Properties props = FACTORY.createPropertiesData(properties);
+
+        // validate properties according to type
+        try {
+            TypeValidator.validateProperties(Arrays.asList(primaryType, secondaryType1, secondaryType2),
props, true);
+            fail("TypeValidator should throw CMISConstraintException if property is not known
in type.");
+        } catch (CmisConstraintException e) {
+            assertTrue(e.getMessage().contains("properties are not known in any of the types"));
+            assertTrue(e.getMessage().contains(unknownPropertyId));
+        }
+    }
+
+    private static List<PropertyData<?>> createPropertiesWithSecondaryTypes(String
typeIdPrimary, List<String> secondaryTypeIds) {
+        List<PropertyData<?>> properties = new ArrayList<PropertyData<?>>();
+        properties.add(FACTORY.createPropertyIdData(PropertyIds.NAME, "Document_1"));
+        properties.add(FACTORY.createPropertyIdData(PropertyIds.OBJECT_TYPE_ID, typeIdPrimary));
+        properties.add(FACTORY.createPropertyIdData(PropertyIds.OBJECT_TYPE_ID, secondaryTypeIds));
+        properties.add(FACTORY.createPropertyBooleanData("BooleanProp", true));
+        properties.add(FACTORY.createPropertyIntegerData(INT_PROP_TYPE, BigInteger.valueOf(0)));
+        properties.add(FACTORY.createPropertyDecimalData(DECIMAL_PROP_TYPE, BigDecimal.valueOf(0.5)));
      
+        return properties;
+    }
+
+
     /**
      * create sample type
      * 

Modified: chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-support/src/main/java/org/apache/chemistry/opencmis/server/support/TypeValidator.java
URL: http://svn.apache.org/viewvc/chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-support/src/main/java/org/apache/chemistry/opencmis/server/support/TypeValidator.java?rev=1454478&r1=1454477&r2=1454478&view=diff
==============================================================================
--- chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-support/src/main/java/org/apache/chemistry/opencmis/server/support/TypeValidator.java
(original)
+++ chemistry/opencmis/trunk/chemistry-opencmis-server/chemistry-opencmis-server-support/src/main/java/org/apache/chemistry/opencmis/server/support/TypeValidator.java
Fri Mar  8 17:40:34 2013
@@ -21,6 +21,7 @@ package org.apache.chemistry.opencmis.se
 import java.math.BigDecimal;
 import java.math.BigInteger;
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Map;
@@ -158,7 +159,7 @@ public class TypeValidator {
         /**
          * Calculate the list of allowed values for this property definition by
          * recursively collecting all choice values from property definition
-         *
+         * 
          * @param propDef
          *            property definition
          * @return list of possible values in complete hierarchy
@@ -233,8 +234,7 @@ public class TypeValidator {
 
             long maxLen = ((PropertyStringDefinition) propDef).getMaxLength() == null ? -1
                     : ((PropertyStringDefinition) propDef).getMaxLength().longValue();
-            long len = property.getFirstValue() == null ? -1
-                    : property.getFirstValue().length();
+            long len = property.getFirstValue() == null ? -1 : property.getFirstValue().length();
 
             // check max length
             if (maxLen >= 0 && len >= 0 && maxLen < len) {
@@ -245,18 +245,13 @@ public class TypeValidator {
     }
 
     public static <T> void validateProperties(TypeDefinition typeDef, Properties properties,
boolean checkMandatory) {
-        validateProperties(typeDef, properties, false, checkMandatory, false);
+        validateProperties(typeDef, properties, checkMandatory, false);
     }
 
     public static <T> void validateProperties(TypeDefinition typeDef, Properties properties,
boolean checkMandatory, boolean cmis11) {
-
-        validateProperties(typeDef, properties, false, checkMandatory, cmis11);
-    }
-
-    public static <T> void validateProperties(TypeDefinition typeDef, Properties properties,
boolean allowUnknowns, boolean checkMandatory, boolean cmis11) {
         List<String> propDefsRequired = getMandatoryPropDefs(typeDef.getPropertyDefinitions());
 
-        if(properties != null) {
+        if (properties != null) {
             for (PropertyData<?> prop : properties.getProperties().values()) {
                 String propertyId = prop.getId();
                 BaseTypeId baseTypeId = typeDef.getBaseTypeId();
@@ -273,23 +268,75 @@ public class TypeValidator {
                 // Check if all properties are known in the type
                 if (typeContainsProperty(typeDef, propertyId)) {
                     // check all type specific constraints:
-                    PropertyDefinition<T> propDef = getPropertyDefinition(typeDef,
-                            propertyId);
+                    PropertyDefinition<T> propDef = getPropertyDefinition(typeDef,
propertyId);
                     PropertyValidator<T> validator = createPropertyValidator(propDef);
                     validator.validate(propDef, (PropertyData<T>) prop);
-                }
-                else if (!allowUnknowns) {
-                    throw new CmisConstraintException("Unknown property "
-                            + propertyId + " in type " + typeDef.getId());
+                } else {
+                    throw new CmisConstraintException("Unknown property " + propertyId +
" in type " + typeDef.getId());
                 }
             }
         }
 
         if (checkMandatory && !propDefsRequired.isEmpty()) {
             throw new CmisConstraintException("The following mandatory properties are missing:
" + propDefsRequired);
-        }    
+        }
+    }
+
+    public static <T> void validateProperties(List<TypeDefinition> typeDefs,
Properties properties,
+            boolean checkMandatory) {
+        if (properties == null)
+            return;
+
+        Map<String, Boolean> checkedProperties = new HashMap<String, Boolean>();
+        for (String propId : properties.getProperties().keySet()) {
+            checkedProperties.put(propId, false);
+        }
+
+        for (TypeDefinition typeDef : typeDefs) {
+
+            List<String> propDefsRequired = getMandatoryPropDefs(typeDef.getPropertyDefinitions());
+
+            for (PropertyData<?> prop : properties.getProperties().values()) {
+                String propertyId = prop.getId();
+                BaseTypeId baseTypeId = typeDef.getBaseTypeId();
+
+                // check that all mandatory attributes are present
+                if (checkMandatory && propDefsRequired.contains(propertyId)) {
+                    propDefsRequired.remove(propertyId);
+                }
+
+                if (isSystemProperty(baseTypeId, propertyId, true)) {
+                    checkedProperties.put(prop.getId(), true); // ignore system properties
for validation
+                } else if (typeContainsProperty(typeDef, propertyId)) {
+                    // Check if all properties are known in the type
+                    // marked the property as found in a type of primary or
+                    // secondary types
+                    checkedProperties.put(prop.getId(), true);
+
+                    // check all type specific constraints:
+                    PropertyDefinition<T> propDef = getPropertyDefinition(typeDef,
propertyId);
+                    PropertyValidator<T> validator = createPropertyValidator(propDef);
+                    validator.validate(propDef, (PropertyData<T>) prop);
+                }
+            }
+
+            if (checkMandatory && !propDefsRequired.isEmpty()) {
+                throw new CmisConstraintException("The following mandatory properties are
missing: " + propDefsRequired);
+            }
+        }
+
+        // check if all properties are known in a type definition
+        List<String> unknownProperties = new ArrayList<String>();
+        for (String propId : properties.getProperties().keySet()) {
+            if (!checkedProperties.get(propId))
+                unknownProperties.add(propId);
+        }
+        if (!unknownProperties.isEmpty()) {
+            throw new CmisConstraintException(
+                    "The following properties are not known in any of the types of this object:
" + unknownProperties);
+        }
     }
-    
+
     public static void validateVersionStateForCreate(DocumentTypeDefinition typeDef, VersioningState
verState) {
         if (null == verState) {
             return;
@@ -303,44 +350,43 @@ public class TypeValidator {
 
     public static void validateAllowedChildObjectTypes(TypeDefinition childTypeDef, List<String>
allowedChildTypes) {
 
-     	validateAllowedTypes(childTypeDef, allowedChildTypes, "in this folder");
+        validateAllowedTypes(childTypeDef, allowedChildTypes, "in this folder");
     }
-    
-    public static void validateAllowedRelationshipTypes (RelationshipTypeDefinition relationshipTypeDef,
TypeDefinition sourceTypeDef,
- 		   TypeDefinition targetTypeDef)
-    {
-    	List<String> allowedSourceTypes = relationshipTypeDef.getAllowedSourceTypeIds();

-    	validateAllowedTypes(sourceTypeDef, allowedSourceTypes, " as source type in this relationship");
-      	List<String> allowedTargetTypes = relationshipTypeDef.getAllowedTargetTypeIds();
-        validateAllowedTypes(targetTypeDef, allowedTargetTypes, " as target type in this
relationship");	
-    }
-    
-    protected static void validateAllowedTypes(TypeDefinition typeDef, List<String>
allowedTypes, String description)
-    {
-    	 if (null == allowedTypes || allowedTypes.size() == 0)
-             return; // all types are allowed
-
-         for (String allowedType : allowedTypes) {
-             if (allowedType.equals(typeDef.getId()))
-                 return;
-         }
-         throw new CmisConstraintException("The requested type " + typeDef.getId() + " is
not allowed " + description);
-     }
-    	 
-    public static void  validateAcl(TypeDefinition typeDef, Acl addACEs, Acl removeACEs)
-    {
-    	if (!typeDef.isControllableAcl() && (addACEs != null || removeACEs != null))
-    	{
-    		throw new CmisConstraintException("acl set for type: " + typeDef.getDisplayName() +
" that is not controllableACL");
-    	}
+
+    public static void validateAllowedRelationshipTypes(RelationshipTypeDefinition relationshipTypeDef,
+            TypeDefinition sourceTypeDef, TypeDefinition targetTypeDef) {
+        List<String> allowedSourceTypes = relationshipTypeDef.getAllowedSourceTypeIds();
+        validateAllowedTypes(sourceTypeDef, allowedSourceTypes, " as source type in this
relationship");
+        List<String> allowedTargetTypes = relationshipTypeDef.getAllowedTargetTypeIds();
+        validateAllowedTypes(targetTypeDef, allowedTargetTypes, " as target type in this
relationship");
     }
-    
+
+    protected static void validateAllowedTypes(TypeDefinition typeDef, List<String>
allowedTypes, String description) {
+        if (null == allowedTypes || allowedTypes.size() == 0)
+            return; // all types are allowed
+
+        for (String allowedType : allowedTypes) {
+            if (allowedType.equals(typeDef.getId()))
+                return;
+        }
+        throw new CmisConstraintException("The requested type " + typeDef.getId() + " is
not allowed " + description);
+    }
+
+    public static void validateAcl(TypeDefinition typeDef, Acl addACEs, Acl removeACEs) {
+        if (!typeDef.isControllableAcl() && (addACEs != null || removeACEs != null))
{
+            throw new CmisConstraintException("acl set for type: " + typeDef.getDisplayName()
+                    + " that is not controllableACL");
+        }
+    }
+
     public static void validateContentAllowed(DocumentTypeDefinition typeDef, boolean hasContent)
{
         ContentStreamAllowed contentAllowed = typeDef.getContentStreamAllowed();
         if (ContentStreamAllowed.REQUIRED == contentAllowed && !hasContent) {
-            throw new CmisConstraintException("Type " + typeDef.getId() + " requires content
but document has no content.");
+            throw new CmisConstraintException("Type " + typeDef.getId()
+                    + " requires content but document has no content.");
         } else if (ContentStreamAllowed.NOTALLOWED == contentAllowed && hasContent)
{
-            throw new CmisConstraintException("Type " + typeDef.getId() + " does not allow
content but document has content.");
+            throw new CmisConstraintException("Type " + typeDef.getId()
+                    + " does not allow content but document has content.");
         }
     }
 



Mime
View raw message