You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@chemistry.apache.org by lg...@apache.org on 2014/04/17 13:11:02 UTC

svn commit: r1588209 [2/2] - in /chemistry/objectivecmis/branches/browser-binding: ObjectiveCMIS.xcodeproj/ ObjectiveCMIS/Bindings/ ObjectiveCMIS/Bindings/AtomPub/ ObjectiveCMIS/Bindings/AtomPub/AtomPubParser/ ObjectiveCMIS/Bindings/Browser/ ObjectiveC...

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserUtil.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserUtil.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserUtil.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserUtil.m Thu Apr 17 11:11:01 2014
@@ -22,6 +22,13 @@
 #import "CMISBrowserConstants.h"
 #import "CMISRepositoryInfo.h"
 #import "CMISPropertyDefinition.h"
+#import "CMISRenditionData.h"
+#import "CMISDocumentTypeDefinition.h"
+#import "CMISFolderTypeDefinition.h"
+#import "CMISRelationshipTypeDefinition.h"
+#import "CMISItemTypeDefinition.h"
+#import "CMISSecondaryTypeDefinition.h"
+#import "CMISErrors.h"
 
 @implementation CMISBrowserUtil
 
@@ -44,18 +51,33 @@
             repoInfo.identifier = repo[kCMISBrowserJSONRepositoryId];
             repoInfo.name = repo[kCMISBrowserJSONRepositoryName];
             repoInfo.desc = repo[kCMISBrowserJSONRepositoryDescription];
-            repoInfo.rootFolderId = repo[kCMISBrowserJSONRootFolderId];
-            repoInfo.cmisVersionSupported = repo[kCMISBrowserJSONCMISVersionSupported];
+            repoInfo.vendorName = repo[kCMISBrowserJSONVendorName];
             repoInfo.productName = repo[kCMISBrowserJSONProductName];
             repoInfo.productVersion = repo[kCMISBrowserJSONProductVersion];
-            repoInfo.vendorName = repo[kCMISBrowserJSONVendorName];
+            repoInfo.rootFolderId = repo[kCMISBrowserJSONRootFolderId];
+            repoInfo.repositoryUrl = repo[kCMISBrowserJSONRepositoryUrl];
+            repoInfo.rootFolderUrl = repo[kCMISBrowserJSONRootFolderUrl];
+            
+            repoInfo.repositoryCapabilities = repo[kCMISBrowserJSONCapabilities]; //TODO should be own type instead of dictionary
+            //TOOD aclCapabilities
+            repoInfo.latestChangeLogToken = repo[kCMISBrowserJSONLatestChangeLogToken];
+            
+            repoInfo.cmisVersionSupported = repo[kCMISBrowserJSONCMISVersionSupported];
+            repoInfo.thinClientUri = repo[kCMISBrowserJSONThinClientUri];
+
+            //TODO repoInfo.changesIncomplete = repo[kCMISBrowserJSONChangesIncomplete];
+            //TODO changesOnType
+
             repoInfo.principalIdAnonymous = repo[kCMISBrowserJSONPrincipalIdAnonymous];
             repoInfo.principalIdAnyone = repo[kCMISBrowserJSONPrincipalIdAnyone];
             
+            //handle extensions
+            repoInfo.extensions = [CMISBrowserUtil convertExtensions:repo cmisKeys:[CMISBrowserConstants repositoryInfoKeys]];
+            
             // store the repo and root folder URLs in the session (when the repoId matches)
             if ([repoInfo.identifier isEqualToString:bindingSession.repositoryId]) {
-                [bindingSession setObject:repo[kCMISBrowserJSONRootFolderUrl] forKey:kCMISBrowserBindingSessionKeyRootFolderUrl];
-                [bindingSession setObject:repo[kCMISBrowserJSONRepositoryUrl] forKey:kCMISBrowserBindingSessionKeyRepositoryUrl];
+                [bindingSession setObject:repoInfo.rootFolderUrl forKey:kCMISBrowserBindingSessionKeyRootFolderUrl];
+                [bindingSession setObject:repoInfo.repositoryUrl forKey:kCMISBrowserBindingSessionKeyRepositoryUrl];
             }
             
             [repositories setObject:repoInfo forKey:repoInfo.identifier];
@@ -75,89 +97,80 @@
     
     CMISTypeDefinition *typeDef = nil;
     if (!serialisationError) {
-        typeDef = [CMISTypeDefinition new];
-        typeDef.id = jsonDictionary[kCMISBrowserJSONId];
-        typeDef.localName = jsonDictionary[kCMISBrowserJSONLocalName];
-        typeDef.localNameSpace = jsonDictionary[kCMISBrowserJSONLocalNamespace];
-        typeDef.displayName = jsonDictionary[kCMISBrowserJSONDisplayName];
-        typeDef.queryName = jsonDictionary[kCMISBrowserJSONQueryName];
-        typeDef.description = jsonDictionary[kCMISBrowserJSONDescription];
-        
-        NSString *baseIdString = jsonDictionary[kCMISBrowserJSONBaseId];
-        if ([baseIdString isEqualToString:kCMISPropertyObjectTypeIdValueDocument]) {
-            typeDef.baseTypeId = CMISBaseTypeDocument;
-        } else if ([baseIdString isEqualToString:kCMISPropertyObjectTypeIdValueFolder]) {
-            typeDef.baseTypeId = CMISBaseTypeFolder;
+        //TODO check for valid baseTypeId (cmis:document, cmis:folder, cmis:relationship, cmis:policy, [cmis:item, cmis:secondary])
+        CMISBaseType baseType = [CMISEnums enumForBaseId:jsonDictionary[kCMISBrowserJSONBaseId]];
+        switch (baseType) {
+            case CMISBaseTypeDocument:
+                typeDef = [CMISDocumentTypeDefinition new];
+                ((CMISDocumentTypeDefinition*)typeDef).contentStreamAllowed = [CMISEnums enumForContentStreamAllowed:jsonDictionary[kCMISBrowserJSONContentStreamAllowed]];
+                ((CMISDocumentTypeDefinition*)typeDef).versionable = [jsonDictionary[kCMISBrowserJSONVersionable] boolValue];
+                break;
+            case CMISBaseTypeFolder:
+                typeDef = [CMISFolderTypeDefinition new];
+                break;
+                
+            case CMISBaseTypeRelationship: {
+                typeDef = [CMISRelationshipTypeDefinition new];
+                
+                id allowedSourceTypes = jsonDictionary[kCMISBrowserJSONAllowedSourceTypes];
+                if([allowedSourceTypes isKindOfClass:NSArray.class]){
+                    NSMutableArray *types = [[NSMutableArray alloc] init];
+                    for (id type in allowedSourceTypes) {
+                        if(type){
+                            [types addObject:type];
+                        }
+                    }
+                    ((CMISRelationshipTypeDefinition*)typeDef).allowedSourceTypes = types;
+                }
+                
+                id allowedTargetTypes = jsonDictionary[kCMISBrowserJSONAllowedTargetTypes];
+                if([allowedTargetTypes isKindOfClass:NSArray.class]){
+                    NSMutableArray *types = [[NSMutableArray alloc] init];
+                    for (id type in allowedTargetTypes) {
+                        if(type){
+                            [types addObject:type];
+                        }
+                    }
+                    ((CMISRelationshipTypeDefinition*)typeDef).allowedTargetTypes = types;
+                }
+                break;
+            }
+            case CMISBaseTypeItem:
+                typeDef = [CMISItemTypeDefinition new];
+                break;
+            case CMISBaseTypeSecondary:
+                typeDef = [CMISSecondaryTypeDefinition new];
+                break;
+            default:
+                if (outError != NULL) *outError = [CMISErrors createCMISErrorWithCode:kCMISErrorCodeInvalidArgument detailedDescription:[NSString stringWithFormat:@"Type '%@' does not match a base type!", jsonDictionary[kCMISBrowserJSONBaseId]]];
+                return nil;
         }
-        
+
+        typeDef.baseTypeId = baseType;
+        typeDef.description = jsonDictionary[kCMISBrowserJSONDescription];
+        typeDef.displayName = jsonDictionary[kCMISBrowserJSONDisplayName];
+        typeDef.id = jsonDictionary[kCMISBrowserJSONId];
+        typeDef.controllablePolicy = [jsonDictionary[kCMISBrowserJSONControllablePolicy] boolValue];
+        typeDef.controllableAcl = [jsonDictionary[kCMISBrowserJSONControllableAcl] boolValue];
         typeDef.creatable = [jsonDictionary[kCMISBrowserJSONCreateable] boolValue];
         typeDef.fileable = [jsonDictionary[kCMISBrowserJSONFileable] boolValue];
-        typeDef.queryable = [jsonDictionary[kCMISBrowserJSONQueryable] boolValue];
         typeDef.fullTextIndexed = [jsonDictionary[kCMISBrowserJSONFullTextIndexed] boolValue];
         typeDef.includedInSupertypeQuery = [jsonDictionary[kCMISBrowserJSONIncludedInSuperTypeQuery] boolValue];
-        typeDef.controllablePolicy = [jsonDictionary[kCMISBrowserJSONControllablePolicy] boolValue];
-        typeDef.controllableAcl = [jsonDictionary[kCMISBrowserJSONControllableAcl] boolValue];
+        typeDef.queryable = [jsonDictionary[kCMISBrowserJSONQueryable] boolValue];
+        typeDef.localName = jsonDictionary[kCMISBrowserJSONLocalName];
+        typeDef.localNameSpace = jsonDictionary[kCMISBrowserJSONLocalNamespace];
+        typeDef.parentTypeId = jsonDictionary[kCMISBrowserJSONParentId];
+        typeDef.queryName = jsonDictionary[kCMISBrowserJSONQueryName];
+        
+        //TODO type mutability
         
         NSDictionary *propertyDefinitions = jsonDictionary[kCMISBrowserJSONPropertyDefinitions];
-        for (NSDictionary *propertyDictionary in [propertyDefinitions allValues]) {
-            // create property definition and add to type definition
-            CMISPropertyDefinition *propDef = [CMISPropertyDefinition new];
-            propDef.id = propertyDictionary[kCMISBrowserJSONId];
-            propDef.localName = propertyDictionary[kCMISBrowserJSONLocalName];
-            propDef.localNamespace = propertyDictionary[kCMISBrowserJSONLocalNamespace];
-            propDef.displayName = propertyDictionary[kCMISBrowserJSONDisplayName];
-            propDef.queryName = propertyDictionary[kCMISBrowserJSONQueryName];
-            propDef.description = propertyDictionary[kCMISBrowserJSONDescription];
-            propDef.inherited = [propertyDictionary[kCMISBrowserJSONInherited] boolValue];
-            propDef.required = [propertyDictionary[kCMISBrowserJSONRequired] boolValue];
-            propDef.queryable = [propertyDictionary[kCMISBrowserJSONQueryable] boolValue];
-            propDef.orderable = [propertyDictionary[kCMISBrowserJSONOrderable] boolValue];
-            
-            // determine property type
-            NSString *typeString = propertyDictionary[kCMISBrowserJSONPropertyType];
-            if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueString]) {
-                propDef.propertyType = CMISPropertyTypeString;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueId]) {
-                propDef.propertyType = CMISPropertyTypeId;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueInteger]) {
-                propDef.propertyType = CMISPropertyTypeInteger;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueDecimal]) {
-                propDef.propertyType = CMISPropertyTypeDecimal;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueBoolean]) {
-                propDef.propertyType = CMISPropertyTypeBoolean;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueDateTime]) {
-                propDef.propertyType = CMISPropertyTypeDateTime;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueHtml]) {
-                propDef.propertyType = CMISPropertyTypeHtml;
-            } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueUri]) {
-                propDef.propertyType = CMISPropertyTypeUri;
-            }
-            
-            // determine cardinality
-            NSString *cardinalityString = propertyDictionary[kCMISBrowserJSONCardinality];
-            if ([cardinalityString isEqualToString:kCMISBrowserJSONCardinalityValueSingle]) {
-                propDef.cardinality = CMISCardinalitySingle;
-            } else if ([cardinalityString isEqualToString:kCMISBrowserJSONCardinalityValueMultiple]) {
-                propDef.cardinality = CMISCardinalityMulti;
-            }
-            
-            // determine updatability
-            NSString *updatabilityString = propertyDictionary[kCMISBrowserJSONUpdateability];
-            if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueReadOnly]) {
-                propDef.updatability = CMISUpdatabilityReadOnly;
-            } else if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueReadWrite]) {
-                propDef.updatability = CMISUpdatabilityReadWrite;
-            } else if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueOnCreate]) {
-                propDef.updatability = CMISUpdatabilityOnCreate;
-            } else if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueWhenCheckedOut]) {
-                propDef.updatability = CMISUpdatabilityWhenCheckedOut;
-            }
-            
-            // TODO: look for restricted choices
-            propDef.openChoice = YES;
-            
-            [typeDef addPropertyDefinition:propDef];
+        for (NSDictionary *propertyDefDictionary in [propertyDefinitions allValues]) {
+            [typeDef addPropertyDefinition:[CMISBrowserUtil convertPropertyDefinition:propertyDefDictionary]];
         }
+        
+        // handle extensions
+        typeDef.extensions = [CMISBrowserUtil convertExtensions:jsonDictionary cmisKeys:[CMISBrowserConstants typeKeys]];
     }
     
     return typeDef;
@@ -174,7 +187,7 @@
     CMISObjectData *objectData = nil;
     if (!serialisationError) {
         // parse the json into a CMISObjectData object
-        objectData = [CMISBrowserUtil objectDataFromDictionary:jsonDictionary];
+        objectData = [CMISBrowserUtil convertObject:jsonDictionary];
     }
     
     return objectData;
@@ -194,34 +207,68 @@
         objectList = [CMISObjectList new];
         
         // parse the objects
-        NSArray *objectsArray = jsonDictionary[@"objects"];
+        NSArray *objectsArray;
+        if([jsonDictionary isKindOfClass:NSArray.class]){ // is NSArray
+            objectsArray = jsonDictionary;
+            
+            objectList.hasMoreItems = NO;
+            objectList.numItems = (int)objectsArray.count;
+        } else { // is NSDictionary
+            objectsArray = jsonDictionary[kCMISBrowserJSONObjects];
+            
+            // retrieve the paging data
+            objectList.hasMoreItems = [jsonDictionary[kCMISBrowserJSONHasMoreItems] boolValue];
+            objectList.numItems = [jsonDictionary[kCMISBrowserJSONNumberItems] intValue];
+        }
         if (objectsArray) {
             NSMutableArray *objects = [NSMutableArray arrayWithCapacity:objectsArray.count];
             for (NSDictionary *dictionary in objectsArray) {
-                NSDictionary *objectDictionary = dictionary[@"object"];
-                CMISObjectData *objectData = [CMISBrowserUtil objectDataFromDictionary:objectDictionary];
-                [objects addObject:objectData];
+                NSDictionary *objectDictionary = dictionary[kCMISBrowserJSONObject];
+                if(!objectDictionary) {
+                    objectDictionary = dictionary;
+                }
+                CMISObjectData *objectData = [CMISBrowserUtil convertObject:objectDictionary];
+                if(objectData){
+                    [objects addObject:objectData];
+                }
             }
             
             // pass objects to list
             objectList.objects = objects;
         }
-        
-        // retrieve the paging data
-        objectList.hasMoreItems = [jsonDictionary[@"hasMoreItems"] boolValue];
-        objectList.numItems = [jsonDictionary[@"numItems"] intValue];
     }
     
     return objectList;
 }
 
++ (NSArray *)renditionsFromJSONData:(NSData *)jsonData error:(NSError **)outError
+{
+    // TODO: error handling i.e. if jsonData is nil, also handle outError being nil
+    
+    // parse the JSON response
+    NSError *serialisationError = nil;
+    id jsonDictionary = [NSJSONSerialization JSONObjectWithData:jsonData options:0 error:&serialisationError];
+    
+    NSArray *renditions = nil;
+    if (!serialisationError) {
+        // parse the json into a CMISObjectData object
+        renditions = [CMISBrowserUtil renditionsFromArray:jsonDictionary];
+    }
+    
+    return renditions;
+}
+
 #pragma mark -
 #pragma mark Private helper methods
 
-+ (CMISObjectData *)objectDataFromDictionary:(NSDictionary *)dictionary
++ (CMISObjectData *)convertObject:(NSDictionary *)dictionary
 {
+    if(!dictionary) {
+        return nil;
+    }
+    
     CMISObjectData *objectData = [CMISObjectData new];
-    NSDictionary *propertiesJson = dictionary[@"succinctProperties"];
+    NSDictionary *propertiesJson = dictionary[kCMISBrowserJSONSuccinctProperties];
     objectData.identifier = propertiesJson[kCMISPropertyObjectId];
     
     // determine the object type
@@ -232,6 +279,50 @@
         objectData.baseType = CMISBaseTypeFolder;
     }
     
+    // set the properties
+    NSDictionary *propertiesExtension = dictionary[kCMISBrowserJSONPropertiesExtension];
+    objectData.properties = [CMISBrowserUtil convertSuccinctProperties:propertiesJson propertiesExtension:propertiesExtension];
+    
+    // relationships
+    NSArray *relationshipsJson = dictionary[kCMISBrowserJSONRelationships];
+    objectData.relationships = [CMISBrowserUtil convertObjects:relationshipsJson];
+    
+    //renditions
+    NSArray *renditionsJson = dictionary[kCMISBrowserJSONRenditions];
+    objectData.renditions = [self renditionsFromArray:renditionsJson];
+    
+    // handle extensions
+    objectData.extensions = [CMISBrowserUtil convertExtensions:dictionary cmisKeys:[CMISBrowserConstants objectKeys]];
+    
+    return objectData;
+}
+
++ (NSArray *)convertObjects:(NSArray *)json
+{
+    if (!json){
+        return nil;
+    }
+    
+    NSMutableArray *result = [[NSMutableArray alloc] init];
+    for (id obj in json) {
+        //TODO check if obj is NSDictionary or else abort with error
+        CMISObjectData *relationship = [CMISBrowserUtil convertObject:obj];
+        if(relationship){
+            [result addObject:relationship];
+        }
+    }
+    
+    return result;
+}
+
++ (CMISProperties *)convertSuccinctProperties:(NSDictionary *)propertiesJson propertiesExtension:(NSDictionary *)extJson
+{
+    if(!propertiesJson) {
+        return nil;
+    }
+    
+    // TODO convert properties according to typeDefinition
+    
     // create properties
     CMISProperties *properties = [CMISProperties new];
     NSArray *propNames = [propertiesJson allKeys];
@@ -248,10 +339,177 @@
         [properties addProperty:propertyData];
     }
     
-    // set the properties
-    objectData.properties = properties;
+    if(extJson){
+        properties.extensions = [CMISBrowserUtil convertExtensions:extJson cmisKeys:[NSSet set]];
+    }
     
-    return objectData;
+    return properties;
+}
+
++ (NSArray *)renditionsFromArray:(NSArray *)array
+{
+    if(!array) {
+        return nil;
+    }
+    NSMutableArray *renditions = [[NSMutableArray alloc] initWithCapacity:array.count];
+    for(NSDictionary *renditionJson in array){
+        CMISRenditionData *renditionData = [CMISRenditionData new];
+        renditionData.height = [NSNumber numberWithLongLong:[renditionJson[kCMISBrowserJSONRenditionHeight] longLongValue]];
+        renditionData.kind = renditionJson[kCMISBrowserJSONRenditionKind];
+        renditionData.length = [NSNumber numberWithLongLong:[renditionJson[kCMISBrowserJSONRenditionLength] longLongValue]];
+        renditionData.mimeType = renditionJson[kCMISBrowserJSONRenditionMimeType];
+        renditionData.renditionDocumentId = renditionJson[kCMISBrowserJSONRenditionDocumentId];
+        renditionData.streamId = renditionJson[kCMISBrowserJSONRenditionStreamId];
+        renditionData.title = renditionJson[kCMISBrowserJSONRenditionTitle];
+        renditionData.width = [NSNumber numberWithLongLong:[renditionJson[kCMISBrowserJSONRenditionWidth] longLongValue]];
+        
+        // handle extensions
+        renditionData.extensions = [CMISBrowserUtil convertExtensions:renditionJson cmisKeys:[CMISBrowserConstants renditionKeys]];
+        
+        [renditions addObject:renditionData];
+    }
+    
+    return renditions;
+}
+
++ (CMISPropertyDefinition *)convertPropertyDefinition:(NSDictionary *)propertyDictionary
+{
+    if(!propertyDictionary){
+        return nil;
+    }
+    
+    // create property definition and add to type definition
+    CMISPropertyDefinition *propDef = [CMISPropertyDefinition new];
+    propDef.id = propertyDictionary[kCMISBrowserJSONId];
+    propDef.localName = propertyDictionary[kCMISBrowserJSONLocalName];
+    propDef.localNamespace = propertyDictionary[kCMISBrowserJSONLocalNamespace];
+    propDef.queryName = propertyDictionary[kCMISBrowserJSONQueryName];
+    propDef.description = propertyDictionary[kCMISBrowserJSONDescription];
+    propDef.displayName = propertyDictionary[kCMISBrowserJSONDisplayName];
+    propDef.inherited = [propertyDictionary[kCMISBrowserJSONInherited] boolValue];
+    propDef.openChoice = [propertyDictionary[kCMISBrowserJSONOpenChoice] boolValue];
+    propDef.orderable = [propertyDictionary[kCMISBrowserJSONOrderable] boolValue];
+    propDef.queryable = [propertyDictionary[kCMISBrowserJSONQueryable] boolValue];
+    propDef.required = [propertyDictionary[kCMISBrowserJSONRequired] boolValue];
+    
+    // determine property type
+    NSString *typeString = propertyDictionary[kCMISBrowserJSONPropertyType];
+    if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueString]) {
+        propDef.propertyType = CMISPropertyTypeString;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueId]) {
+        propDef.propertyType = CMISPropertyTypeId;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueInteger]) {
+        propDef.propertyType = CMISPropertyTypeInteger;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueDecimal]) {
+        propDef.propertyType = CMISPropertyTypeDecimal;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueBoolean]) {
+        propDef.propertyType = CMISPropertyTypeBoolean;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueDateTime]) {
+        propDef.propertyType = CMISPropertyTypeDateTime;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueHtml]) {
+        propDef.propertyType = CMISPropertyTypeHtml;
+    } else if ([typeString isEqualToString:kCMISBrowserJSONPropertyTypeValueUri]) {
+        propDef.propertyType = CMISPropertyTypeUri;
+    }
+    
+    // determine cardinality
+    NSString *cardinalityString = propertyDictionary[kCMISBrowserJSONCardinality];
+    if ([cardinalityString isEqualToString:kCMISBrowserJSONCardinalityValueSingle]) {
+        propDef.cardinality = CMISCardinalitySingle;
+    } else if ([cardinalityString isEqualToString:kCMISBrowserJSONCardinalityValueMultiple]) {
+        propDef.cardinality = CMISCardinalityMulti;
+    }
+    
+    // determine updatability
+    NSString *updatabilityString = propertyDictionary[kCMISBrowserJSONUpdateability];
+    if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueReadOnly]) {
+        propDef.updatability = CMISUpdatabilityReadOnly;
+    } else if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueReadWrite]) {
+        propDef.updatability = CMISUpdatabilityReadWrite;
+    } else if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueOnCreate]) {
+        propDef.updatability = CMISUpdatabilityOnCreate;
+    } else if ([updatabilityString isEqualToString:kCMISBrowserJSONUpdateabilityValueWhenCheckedOut]) {
+        propDef.updatability = CMISUpdatabilityWhenCheckedOut;
+    }
+    
+    // TODO default value
+    
+    // handle extensions
+    propDef.extensions = [CMISBrowserUtil convertExtensions:propertyDictionary cmisKeys:[CMISBrowserConstants propertyTypeKeys]];
+    
+    return propDef;
+}
+
++ (NSArray *)convertExtensions:(NSDictionary *)source cmisKeys:(NSSet *)cmisKeys
+{
+    if (!source) {
+        return nil;
+    }
+    
+    NSMutableArray *extensions = nil; // array of CMISExtensionElement's
+    
+    for (NSString *key in source.keyEnumerator) {
+        if ([cmisKeys containsObject:key]) {
+            continue;
+        }
+        
+        if (!extensions) {
+            extensions = [[NSMutableArray alloc] init];
+        }
+        
+        id value = source[key];
+        if ([value isKindOfClass:NSDictionary.class]) {
+            [extensions addObject:[[CMISExtensionElement alloc] initNodeWithName:key namespaceUri:nil attributes:nil children:[CMISBrowserUtil convertExtension:value]]];
+        } else if ([value isKindOfClass:NSArray.class]) {
+            [extensions addObjectsFromArray:[CMISBrowserUtil convertExtension: key fromArray:value]];
+        } else {
+            [extensions addObject:[[CMISExtensionElement alloc] initLeafWithName:key namespaceUri:nil attributes:nil value:value]];
+        }
+    }
+    return extensions;
+}
+
++ (NSArray *)convertExtension:(NSDictionary *)dictionary
+{
+    if (!dictionary) {
+        return nil;
+    }
+    
+    NSMutableArray *extensions = [[NSMutableArray alloc] init]; // array of CMISExtensionElement's
+    
+    for (NSString *key in dictionary.keyEnumerator) {
+        id value = dictionary[key];
+        if ([value isKindOfClass:NSDictionary.class]) {
+            [extensions addObject:[[CMISExtensionElement alloc] initNodeWithName:key namespaceUri:nil attributes:nil children:[CMISBrowserUtil convertExtension:value]]];
+        } else if ([value isKindOfClass:NSArray.class]) {
+            [extensions addObjectsFromArray:[CMISBrowserUtil convertExtension: key fromArray:value]];
+        } else {
+            [extensions addObject:[[CMISExtensionElement alloc] initLeafWithName:key namespaceUri:nil attributes:nil value:value]];
+        }
+    }
+    
+    return extensions;
+}
+
++ (NSArray *)convertExtension:(NSString *)key fromArray:(NSArray *)array
+{
+    if (!array) {
+        return nil;
+    }
+    
+    NSMutableArray *extensions = [[NSMutableArray alloc] init]; // array of CMISExtensionElement's
+    
+    for (id element in array) {
+        if ([element isKindOfClass:NSDictionary.class]) {
+            [extensions addObject:[[CMISExtensionElement alloc] initNodeWithName:key namespaceUri:nil attributes:nil children:[CMISBrowserUtil convertExtension:element]]];
+        } else if ([element isKindOfClass:NSArray.class]) {
+            [extensions addObjectsFromArray:[CMISBrowserUtil convertExtension: key fromArray:element]];
+        } else {
+            [extensions addObject:[[CMISExtensionElement alloc] initLeafWithName:key namespaceUri:nil attributes:nil value:element]];
+        }
+    }
+    
+    return extensions;
 }
 
 @end

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserVersioningService.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserVersioningService.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserVersioningService.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/Browser/CMISBrowserVersioningService.m Thu Apr 17 11:11:01 2014
@@ -18,6 +18,12 @@
  */
 
 #import "CMISBrowserVersioningService.h"
+#import "CMISRequest.h"
+#import "CMISBrowserConstants.h"
+#import "CMISHttpResponse.h"
+#import "CMISBrowserUtil.h"
+#import "CMISURLUtil.h"
+#import "CMISConstants.h"
 
 @implementation CMISBrowserVersioningService
 
@@ -31,19 +37,70 @@
                       includeAllowableActions:(BOOL)includeAllowableActions
                               completionBlock:(void (^)(CMISObjectData *objectData, NSError *error))completionBlock
 {
-    NSString * message = [NSString stringWithFormat:@"%s is not implemented yet", __PRETTY_FUNCTION__];
-    NSException *exception = [NSException exceptionWithName:NSInvalidArgumentException reason:message userInfo:nil];
-    @throw exception;
+    NSString *objectUrl = [self getObjectUrlObjectId:objectId selector:kCMISBrowserJSONSelectorObject];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterFilter value:filter urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterIncludeAllowableActions boolValue:includeAllowableActions urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterIncludeRelationships value:[CMISEnums stringForIncludeRelationShip:relationships] urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterRenditionFilter value:renditionFilter urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterIncludePolicyIds boolValue:includePolicyIds urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterIncludeAcl boolValue:includeACL urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterReturnVersion value:[CMISEnums stringForReturnVersion:major] urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterSuccinct value:kCMISParameterValueTrue urlString:objectUrl];
+    
+    CMISRequest *cmisRequest = [[CMISRequest alloc] init];
+    
+    [self.bindingSession.networkProvider invokeGET:[NSURL URLWithString:objectUrl]
+                                           session:self.bindingSession
+                                       cmisRequest:cmisRequest
+                                   completionBlock:^(CMISHttpResponse *httpResponse, NSError *error) {
+                                       if (httpResponse.statusCode == 200 && httpResponse.data) {
+                                           NSError *parsingError = nil;
+                                           CMISObjectData *objectData = [CMISBrowserUtil objectDataFromJSONData:httpResponse.data error:&parsingError];
+                                           if (parsingError)
+                                           {
+                                               completionBlock(nil, parsingError);
+                                           } else {
+                                               completionBlock(objectData, nil);
+                                           }
+                                       } else {
+                                           completionBlock(nil, error);
+                                       }
+                                   }];
+    
+    return cmisRequest;
 }
 
 - (CMISRequest*)retrieveAllVersions:(NSString *)objectId
                              filter:(NSString *)filter
             includeAllowableActions:(BOOL)includeAllowableActions
                     completionBlock:(void (^)(NSArray *objects, NSError *error))completionBlock
-{
-    NSString * message = [NSString stringWithFormat:@"%s is not implemented yet", __PRETTY_FUNCTION__];
-    NSException *exception = [NSException exceptionWithName:NSInvalidArgumentException reason:message userInfo:nil];
-    @throw exception;
+{    
+    NSString *objectUrl = [self getObjectUrlObjectId:objectId selector:kCMISBrowserJSONSelectorVersions];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterFilter value:filter urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterIncludeAllowableActions value:(includeAllowableActions ? @"true" : @"false") urlString:objectUrl];
+    objectUrl = [CMISURLUtil urlStringByAppendingParameter:kCMISParameterSuccinct value:@"true" urlString:objectUrl];
+    
+    CMISRequest *cmisRequest = [[CMISRequest alloc] init];
+    
+    [self.bindingSession.networkProvider invokeGET:[NSURL URLWithString:objectUrl]
+                                           session:self.bindingSession
+                                       cmisRequest:cmisRequest
+                                   completionBlock:^(CMISHttpResponse *httpResponse, NSError *error) {
+                                       if (httpResponse.statusCode == 200 && httpResponse.data) {
+                                           NSError *parsingError = nil;
+                                           CMISObjectList *objectList = [CMISBrowserUtil objectListFromJSONData:httpResponse.data error:&parsingError];
+                                           if (!objectList.objects)
+                                           {
+                                               completionBlock(nil, parsingError);
+                                           } else {
+                                               completionBlock(objectList.objects, nil);
+                                           }
+                                       } else {
+                                           completionBlock(nil, error);
+                                       }
+                                   }];
+    
+    return cmisRequest;
 }
 
 /**

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.h Thu Apr 17 11:11:01 2014
@@ -26,6 +26,7 @@
 extern NSString * const kCMISBindingSessionKeyUrl;
 extern NSString * const kCMISBindingSessionKeyObjectByIdUriBuilder;
 extern NSString * const kCMISBindingSessionKeyObjectByPathUriBuilder;
+extern NSString * const kCMISBindingSessionKeyChildrenByIdUriBuilder;
 extern NSString * const kCMISBindingSessionKeyTypeByIdUriBuilder;
 
 @interface CMISBindingSession : NSObject

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISBindingSession.m Thu Apr 17 11:11:01 2014
@@ -22,6 +22,7 @@
 NSString * const kCMISBindingSessionKeyUrl = @"cmis_session_key_url";
 NSString * const kCMISBindingSessionKeyObjectByIdUriBuilder = @"cmis_session_key_objectbyid_uri_builder";
 NSString * const kCMISBindingSessionKeyObjectByPathUriBuilder = @"cmis_session_key_objectbypath_uri_builder";
+NSString * const kCMISBindingSessionKeyChildrenByIdUriBuilder = @"cmis_session_key_childrenbyid_uri_builder";
 NSString * const kCMISBindingSessionKeyTypeByIdUriBuilder = @"cmis_session_key_type_by_id_uri_builder";
 
 @interface CMISBindingSession ()

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.h?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.h (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.h Thu Apr 17 11:11:01 2014
@@ -0,0 +1,26 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import <Foundation/Foundation.h>
+#import "CMISEnums.h"
+#import "CMISTypeDefinition.h"
+
+@interface CMISFolderTypeDefinition : CMISTypeDefinition
+
+@end

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.m?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.m (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISFolderTypeDefinition.m Thu Apr 17 11:11:01 2014
@@ -0,0 +1,24 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import "CMISFolderTypeDefinition.h"
+
+@implementation CMISFolderTypeDefinition
+
+@end

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.h?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.h (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.h Thu Apr 17 11:11:01 2014
@@ -0,0 +1,26 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import <Foundation/Foundation.h>
+#import "CMISEnums.h"
+#import "CMISTypeDefinition.h"
+
+@interface CMISItemTypeDefinition : CMISTypeDefinition
+
+@end

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.m?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.m (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISItemTypeDefinition.m Thu Apr 17 11:11:01 2014
@@ -0,0 +1,24 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import "CMISItemTypeDefinition.h"
+
+@implementation CMISItemTypeDefinition
+
+@end

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISPropertyDefinition.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISPropertyDefinition.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISPropertyDefinition.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISPropertyDefinition.h Thu Apr 17 11:11:01 2014
@@ -19,10 +19,11 @@
 
 #import <Foundation/Foundation.h>
 #import "CMISEnums.h"
+#import "CMISExtensionData.h"
 
 
 // TODO: type specific properties, see cmis spec line 527
-@interface CMISPropertyDefinition : NSObject
+@interface CMISPropertyDefinition : CMISExtensionData
 
 
 @property (nonatomic, strong) NSString *id;

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.h?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.h (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.h Thu Apr 17 11:11:01 2014
@@ -0,0 +1,29 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import <Foundation/Foundation.h>
+#import "CMISEnums.h"
+#import "CMISTypeDefinition.h"
+
+@interface CMISRelationshipTypeDefinition : CMISTypeDefinition
+
+@property (nonatomic, strong) NSArray * allowedSourceTypes;
+@property (nonatomic, strong) NSArray * allowedTargetTypes;
+
+@end

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.m?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.m (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRelationshipTypeDefinition.m Thu Apr 17 11:11:01 2014
@@ -0,0 +1,24 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import "CMISRelationshipTypeDefinition.h"
+
+@implementation CMISRelationshipTypeDefinition
+
+@end

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRenditionData.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRenditionData.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRenditionData.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISRenditionData.h Thu Apr 17 11:11:01 2014
@@ -18,9 +18,9 @@
  */
  
 #import <Foundation/Foundation.h>
+#import "CMISExtensionData.h"
 
-
-@interface CMISRenditionData : NSObject
+@interface CMISRenditionData : CMISExtensionData
 
 /**  Identifies the rendition stream. */
 @property (nonatomic, strong) NSString *streamId;

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.h?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.h (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.h Thu Apr 17 11:11:01 2014
@@ -0,0 +1,26 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import <Foundation/Foundation.h>
+#import "CMISEnums.h"
+#import "CMISTypeDefinition.h"
+
+@interface CMISSecondaryTypeDefinition : CMISTypeDefinition
+
+@end

Added: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.m?rev=1588209&view=auto
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.m (added)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISSecondaryTypeDefinition.m Thu Apr 17 11:11:01 2014
@@ -0,0 +1,24 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements.  See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership.  The ASF licenses this file
+ to you 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.
+ */
+
+#import "CMISSecondaryTypeDefinition.h"
+
+@implementation CMISSecondaryTypeDefinition
+
+@end

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.h Thu Apr 17 11:11:01 2014
@@ -19,11 +19,12 @@
 
 #import <Foundation/Foundation.h>
 #import "CMISEnums.h"
+#import "CMISExtensionData.h"
 
 @class CMISPropertyDefinition;
 
 
-@interface CMISTypeDefinition : NSObject
+@interface CMISTypeDefinition : CMISExtensionData
 
 // TODO: rename "id" property to identifier as id is a reserved keyword in ObjectiveC
 // TODO: rename "description" property to summary as description is a reserved keyword in ObjectiveC
@@ -35,6 +36,7 @@
 @property (nonatomic, strong) NSString *queryName;
 @property (nonatomic, strong) NSString *description;
 @property (nonatomic, assign) CMISBaseType baseTypeId;
+@property (nonatomic, strong) NSString *parentTypeId;
 
 @property (nonatomic, assign, getter = isCreatable) BOOL creatable;
 @property (nonatomic, assign, getter = isFileable) BOOL fileable;

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Bindings/CMISTypeDefinition.m Thu Apr 17 11:11:01 2014
@@ -47,4 +47,13 @@
     return [self.internalPropertyDefinitions objectForKey:propertyId];
 }
 
+-(void)setParentTypeId:(NSString *)parentTypeId
+{
+    if (!parentTypeId || parentTypeId.length == 0) {
+        _parentTypeId = nil;
+    } else {
+        _parentTypeId = parentTypeId;
+    }
+}
+
 @end
\ No newline at end of file

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.h Thu Apr 17 11:11:01 2014
@@ -45,7 +45,50 @@ extern NSString * const kCMISPropertyDes
 // Property values
 extern NSString * const kCMISPropertyObjectTypeIdValueDocument;
 extern NSString * const kCMISPropertyObjectTypeIdValueFolder;
+extern NSString * const kCMISPropertyObjectTypeIdValueRelationship;
+extern NSString * const kCMISPropertyObjectTypeIdValuePolicy;
+extern NSString * const kCMISPropertyObjectTypeIdValueItem;
+extern NSString * const kCMISPropertyObjectTypeIdValueSecondary;
 
 // Session cache keys
 
 extern NSString * const kCMISSessionKeyWorkspaces;
+
+// URL parameters
+extern NSString * const kCMISParameterChangeToken;
+extern NSString * const kCMISParameterOverwriteFlag;
+extern NSString * const kCMISParameterIncludeAllowableActions;
+extern NSString * const kCMISParameterFilter;
+extern NSString * const kCMISParameterMaxItems;
+extern NSString * const kCMISParameterObjectId;
+extern NSString * const kCMISParameterOrderBy;
+extern NSString * const kCMISParameterIncludePathSegment;
+extern NSString * const kCMISParameterIncludeRelationships;
+extern NSString * const kCMISParameterIncludePolicyIds;
+extern NSString * const kCMISParameterIncludeAcl;
+extern NSString * const kCMISParameterRenditionFilter;
+extern NSString * const kCMISParameterSkipCount;
+extern NSString * const kCMISParameterStreamId;
+extern NSString * const kCMISParameterAllVersions;
+extern NSString * const kCMISParameterContinueOnFailure;
+extern NSString * const kCMISParameterUnfileObjects;
+extern NSString * const kCMISParameterRelativePathSegment;
+extern NSString * const kCMISParameterMajor;
+extern NSString * const kCMISParameterCheckin;
+extern NSString * const kCMISParameterCheckinComment;
+extern NSString * const kCMISParameterSelector;
+extern NSString * const kCMISParameterSuccinct;
+extern NSString * const kCMISParameterReturnVersion;
+extern NSString * const kCMISParameterTypeId;
+
+// Parameter Values
+extern NSString * const kCMISParameterValueTrue;
+extern NSString * const kCMISParameterValueFalse;
+extern NSString * const kCMISParameterValueReturnValueThis;
+extern NSString * const kCMISParameterValueReturnValueLatest;
+extern NSString * const kCMISParameterValueReturnValueLatestMajor;
+
+//ContentStreamAllowed enum values
+extern NSString * const kCMISContentStreamAllowedValueRequired;
+extern NSString * const kCMISContentStreamAllowedValueAllowed;
+extern NSString * const kCMISContentStreamAllowedValueNotAllowed;
\ No newline at end of file

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISConstants.m Thu Apr 17 11:11:01 2014
@@ -49,8 +49,50 @@ NSString * const kCMISPropertyDescriptio
 
 NSString * const kCMISPropertyObjectTypeIdValueDocument = @"cmis:document";
 NSString * const kCMISPropertyObjectTypeIdValueFolder = @"cmis:folder";
+NSString * const kCMISPropertyObjectTypeIdValueRelationship = @"cmis:relationship";
+NSString * const kCMISPropertyObjectTypeIdValuePolicy = @"cmis:policy";
+NSString * const kCMISPropertyObjectTypeIdValueItem = @"cmis:item";
+NSString * const kCMISPropertyObjectTypeIdValueSecondary = @"cmis:secondary";
 
 // Session cache keys
 
 NSString * const kCMISSessionKeyWorkspaces = @"cmis_session_key_workspaces";
 
+// Parameters
+NSString * const kCMISParameterChangeToken = @"changeToken";
+NSString * const kCMISParameterOverwriteFlag = @"overwriteFlag";
+NSString * const kCMISParameterIncludeAllowableActions = @"includeAllowableActions";
+NSString * const kCMISParameterFilter = @"filter";
+NSString * const kCMISParameterMaxItems = @"maxItems";
+NSString * const kCMISParameterObjectId = @"objectId";
+NSString * const kCMISParameterOrderBy = @"orderBy";
+NSString * const kCMISParameterIncludePathSegment = @"includePathSegment";
+NSString * const kCMISParameterIncludeRelationships = @"includeRelationships";
+NSString * const kCMISParameterIncludePolicyIds = @"includePolicyIds";
+NSString * const kCMISParameterIncludeAcl = @"includeACL";
+NSString * const kCMISParameterRenditionFilter = @"renditionFilter";
+NSString * const kCMISParameterSkipCount = @"skipCount";
+NSString * const kCMISParameterStreamId = @"streamId";
+NSString * const kCMISParameterAllVersions = @"allVersions";
+NSString * const kCMISParameterContinueOnFailure= @"continueOnFailure";
+NSString * const kCMISParameterUnfileObjects = @"unfileObjects";
+NSString * const kCMISParameterRelativePathSegment = @"includeRelativePathSegment";
+NSString * const kCMISParameterMajor = @"major";
+NSString * const kCMISParameterCheckin = @"checkin";
+NSString * const kCMISParameterCheckinComment = @"checkinComment";
+NSString * const kCMISParameterSelector = @"cmisselector";
+NSString * const kCMISParameterSuccinct = @"succinct";
+NSString * const kCMISParameterReturnVersion = @"returnVersion";
+NSString * const kCMISParameterTypeId = @"typeId";
+
+// Parameter Values
+NSString * const kCMISParameterValueTrue = @"true";
+NSString * const kCMISParameterValueFalse = @"false";
+NSString * const kCMISParameterValueReturnValueThis = @"this";
+NSString * const kCMISParameterValueReturnValueLatest = @"latest";
+NSString * const kCMISParameterValueReturnValueLatestMajor = @"latestmajor";
+
+//ContentStreamAllowed enum values
+NSString * const kCMISContentStreamAllowedValueRequired = @"required";
+NSString * const kCMISContentStreamAllowedValueAllowed = @"allowed";
+NSString * const kCMISContentStreamAllowedValueNotAllowed = @"notallowed";

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.h Thu Apr 17 11:11:01 2014
@@ -30,10 +30,13 @@ typedef NS_ENUM(NSInteger, CMISBindingTy
 // Base type
 typedef NS_ENUM(NSInteger, CMISBaseType)
 {
+    CMISBaseTypeUnknown,
     CMISBaseTypeDocument,
     CMISBaseTypeFolder,
     CMISBaseTypeRelationship,
-    CMISBaseTypePolicy
+    CMISBaseTypePolicy,
+    CMISBaseTypeItem,
+    CMISBaseTypeSecondary
 };
 
 typedef NS_ENUM(NSInteger, CMISIncludeRelationship)
@@ -141,12 +144,25 @@ typedef NS_ENUM(NSInteger, CMISContentSt
 {
     CMISContentStreamNotAllowed,
     CMISContentStreamAllowed,
-    CMISContentStreamRequired
+    CMISContentStreamRequired,
+    CMISContentStreamUnknown
+};
+
+// ReturnVersion
+typedef NS_ENUM(NSInteger, CMISReturnVersion)
+{
+    NOT_PROVIDED,
+    THIS,
+    LATEST,
+    LATEST_MAJOR
 };
 
 @interface CMISEnums : NSObject 
 
 + (NSString *)stringForIncludeRelationShip:(CMISIncludeRelationship)includeRelationship;
 + (NSString *)stringForUnfileObject:(CMISUnfileObject)unfileObject;
++ (NSString *)stringForReturnVersion:(BOOL)major;
++ (CMISBaseType)enumForBaseId:(NSString *)baseId;
++ (CMISContentStreamAllowedType)enumForContentStreamAllowed:(NSString *)contentStreamAllowed;
 
 @end
\ No newline at end of file

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISEnums.m Thu Apr 17 11:11:01 2014
@@ -19,6 +19,7 @@
 
 #import "CMISEnums.h"
 #import "CMISLog.h"
+#import "CMISConstants.h"
 
 @implementation CMISEnums
 
@@ -65,4 +66,41 @@
     return unfileObjectString;
 }
 
++ (NSString *)stringForReturnVersion:(BOOL)major
+{
+    return major == NO ? kCMISParameterValueReturnValueLatest : kCMISParameterValueReturnValueLatestMajor;
+}
+
++ (CMISBaseType)enumForBaseId:(NSString *)baseId
+{
+    if([kCMISPropertyObjectTypeIdValueDocument isEqualToString:baseId]) {
+        return CMISBaseTypeDocument;
+    } else if([kCMISPropertyObjectTypeIdValueFolder isEqualToString:baseId]) {
+        return CMISBaseTypeFolder;
+    } else if([kCMISPropertyObjectTypeIdValueRelationship isEqualToString:baseId]) {
+        return CMISBaseTypeRelationship;
+    } else if([kCMISPropertyObjectTypeIdValuePolicy isEqualToString:baseId]) {
+        return CMISBaseTypePolicy;
+    } else if([kCMISPropertyObjectTypeIdValueItem isEqualToString:baseId]) {
+        return CMISBaseTypeItem;
+    } else if([kCMISPropertyObjectTypeIdValueSecondary isEqualToString:baseId]) {
+        return CMISBaseTypeSecondary;
+    } else {
+        return CMISBaseTypeUnknown;
+    }
+}
+
++ (CMISContentStreamAllowedType)enumForContentStreamAllowed:(NSString *)contentStreamAllowed
+{
+    if([kCMISContentStreamAllowedValueAllowed isEqualToString:contentStreamAllowed]) {
+        return CMISContentStreamAllowed;
+    } else if([kCMISContentStreamAllowedValueNotAllowed isEqualToString:contentStreamAllowed]) {
+        return CMISContentStreamNotAllowed;
+    } else if([kCMISContentStreamAllowedValueRequired isEqualToString:contentStreamAllowed]) {
+        return CMISContentStreamRequired;
+    } else {
+        return CMISContentStreamUnknown;
+    }
+}
+
 @end
\ No newline at end of file

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISObjectData.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISObjectData.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISObjectData.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISObjectData.h Thu Apr 17 11:11:01 2014
@@ -37,5 +37,6 @@
 @property (nonatomic, strong) CMISAllowableActions *allowableActions;
 @property (nonatomic, strong) CMISAcl *acl;
 @property (nonatomic, strong) NSArray *renditions; // An array containing CMISRenditionData objects
+@property (nonatomic, strong) NSArray *relationships; // An array containing CMISObjectData objects; Relationships from and to this object.
 
 @end

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISRepositoryInfo.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISRepositoryInfo.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISRepositoryInfo.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Common/CMISRepositoryInfo.h Thu Apr 17 11:11:01 2014
@@ -26,11 +26,15 @@
 @property (nonatomic, strong) NSString *name;
 @property (nonatomic, strong) NSString *desc;
 @property (nonatomic, strong) NSString *rootFolderId;
+@property (nonatomic, strong) NSString *rootFolderUrl;
+@property (nonatomic, strong) NSString *repositoryUrl;
 
 @property (nonatomic, strong) NSString *cmisVersionSupported;
 @property (nonatomic, strong) NSString *productName;
 @property (nonatomic, strong) NSString *productVersion;
 @property (nonatomic, strong) NSString *vendorName;
+@property (nonatomic, strong) NSString *thinClientUri;
+@property (nonatomic, strong) NSString *latestChangeLogToken;
 
 /**
  * Returns principal ID for an anonymous user (any authenticated user). This

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.h
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.h?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.h (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.h Thu Apr 17 11:11:01 2014
@@ -21,8 +21,15 @@
 
 
 @interface CMISURLUtil : NSObject
-/// utility method to obtain a URL string
+/// utility method to obtain a URL string for given parameter and string value
 + (NSString *)urlStringByAppendingParameter:(NSString *)parameterName value:(NSString *)parameterValue urlString:(NSString *)urlString;
+/// convenient utility method to obtain a URL string for given parameter and boolean value
++ (NSString *)urlStringByAppendingParameter:(NSString *)parameterName boolValue:(BOOL)parameterValue urlString:(NSString *)urlString;
+/// convenient utility method to obtain a URL string for given parameter and boolean value
++ (NSString *)urlStringByAppendingParameter:(NSString *)parameterName numberValue:(NSNumber *)parameterValue urlString:(NSString *)urlString;
+/// utility method to obtain a URL string by appending the given path
++ (NSString *)urlStringByAppendingPath:(NSString *)path urlString:(NSString *)urlString;
+
 /// utility method to obtain a URL string
 + (NSURL *)urlStringByAppendingParameter:(NSString *)parameterName value:(NSString *)parameterValue url:(NSURL *)url;
 

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMIS/Utils/CMISURLUtil.m Thu Apr 17 11:11:01 2014
@@ -18,10 +18,21 @@
  */
  
 #import "CMISURLUtil.h"
+#import "CMISConstants.h"
 
 
 @implementation CMISURLUtil
 
++ (NSString *)urlStringByAppendingParameter:(NSString *)parameterName boolValue:(BOOL)parameterValue urlString:(NSString *)urlString
+{
+    return [CMISURLUtil urlStringByAppendingParameter:parameterName value:parameterValue ? kCMISParameterValueTrue : kCMISParameterValueFalse urlString:urlString];
+}
+
++ (NSString *)urlStringByAppendingParameter:(NSString *)parameterName numberValue:(NSNumber *)parameterValue urlString:(NSString *)urlString
+{
+    return [CMISURLUtil urlStringByAppendingParameter:parameterName value:[parameterValue stringValue] urlString:urlString];
+}
+
 + (NSString *)urlStringByAppendingParameter:(NSString *)parameterName value:(NSString *)parameterValue urlString:(NSString *)urlString
 {
     if (parameterName == nil || parameterValue == nil) {
@@ -34,7 +45,9 @@
     if ([result rangeOfString:@"?"].location == NSNotFound) {
         [result appendString:@"?"];
     } else {
-        [result appendString:@"&"];
+        if([result rangeOfString:@"?"].location != result.length -1){ // Only add ampersand if there is already a parameter added
+            [result appendString:@"&"];
+        }
     }
 
     // Append param
@@ -45,6 +58,13 @@
     return result;
 }
 
++ (NSString *)urlStringByAppendingPath:(NSString *)path urlString:(NSString *)urlString
+{
+    NSURL *url = [[NSURL URLWithString:urlString] URLByAppendingPathComponent:path];
+    
+    return [url absoluteString];
+}
+
 + (NSURL *)urlStringByAppendingParameter:(NSString *)parameterName value:(NSString *)parameterValue url:(NSURL *)url
 {
     return [NSURL URLWithString:[CMISURLUtil urlStringByAppendingParameter:parameterName value:parameterValue urlString:[url absoluteString]]];

Modified: chemistry/objectivecmis/branches/browser-binding/ObjectiveCMISTests/ObjectiveCMISTests.m
URL: http://svn.apache.org/viewvc/chemistry/objectivecmis/branches/browser-binding/ObjectiveCMISTests/ObjectiveCMISTests.m?rev=1588209&r1=1588208&r2=1588209&view=diff
==============================================================================
--- chemistry/objectivecmis/branches/browser-binding/ObjectiveCMISTests/ObjectiveCMISTests.m (original)
+++ chemistry/objectivecmis/branches/browser-binding/ObjectiveCMISTests/ObjectiveCMISTests.m Thu Apr 17 11:11:01 2014
@@ -42,6 +42,7 @@
 #import "CMISErrors.h"
 #import "CMISDateUtil.h"
 #import "CMISLog.h"
+#import "CMISURLUtil.h"
 
 @interface ObjectiveCMISTests ()
 
@@ -295,22 +296,22 @@
                     }
                     
                     
-                    // Bug on Alfresco server. Uncomment when fixed.
                     // Fetch third page, just to be sure
-                    //    CMISPagedResult *thirdPageResult = [secondPageResult fetchNextPageAndReturnError:&error];
-                    //    STAssertNil(error, @"Got error while retrieving children: %@", [error description]);
-                    //    STAssertTrue(thirdPageResult.hasMoreItems, @"There should still be more children");
-                    //    STAssertTrue(thirdPageResult.numItems > 6, @"The test repository should have more than 6 objects");
-                    //    STAssertTrue(thirdPageResult.resultArray.count == 2, @"Expected 2 children in the page, but got %d", thirdPageResult.resultArray.count);
-                    //
-                    //    // Verify if no double object ids were found
-                    //    for (CMISObject *object in thirdPageResult.resultArray)
-                    //    {
-                    //        STAssertTrue(![objectIds containsObject:object.identifier], @"Object was already returned in a previous page. This is a serious impl bug!");
-                    //        [objectIds addObject:object.identifier];
-                    //    }
+                    [secondPageResult fetchNextPageWithCompletionBlock:^(CMISPagedResult *thirdPageResult, NSError *error) {
+                        XCTAssertNil(error, @"Got error while retrieving children: %@", [error description]);
+                        XCTAssertTrue(thirdPageResult.hasMoreItems, @"There should still be more children");
+                        XCTAssertTrue(thirdPageResult.numItems > 6, @"The test repository should have more than 6 objects");
+                        XCTAssertTrue(thirdPageResult.resultArray.count == 2, @"Expected 2 children in the page, but got %lu", (unsigned long)thirdPageResult.resultArray.count);
                     
-                    self.testCompleted = YES;
+                        // Verify if no double object ids were found
+                        for (CMISObject *object in thirdPageResult.resultArray)
+                        {
+                            XCTAssertTrue(![objectIds containsObject:object.identifier], @"Object was already returned in a previous page. This is a serious impl bug!");
+                            [objectIds addObject:object.identifier];
+                        }
+                        
+                        self.testCompleted = YES;
+                    }];
                 }];
             }];
         }];
@@ -338,7 +339,7 @@
             XCTAssertNotNil(document.versionSeriesId, @"Document version series id should not be nil");
             XCTAssertTrue(document.isLatestVersion, @"Document should be latest version");
             //XCTAssertFalse(document.isLatestMajorVersion, @"Document should be latest major version");
-            XCTAssertFalse(document.isMajorVersion, @"Document should be major version");
+            XCTAssertFalse(document.isMajorVersion, @"Document should not be major version");
             
             XCTAssertNotNil(document.contentStreamId, @"Document content stream id should not be nil");
             XCTAssertNotNil(document.contentStreamFileName, @"Document content stream file name should not be nil");
@@ -1879,4 +1880,53 @@
     }];
 }
 
+-(void)testUrlUtilAppendParameter
+{
+    NSString *path;
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"param1" value:@"value1" urlString:@"scheme://host:12345/path?"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path?param1=value1", @"expected url with with one parameter and it's value");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"param1" value:@"value1" urlString:@"scheme://host:12345/path"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path?param1=value1", @"expected url with with one parameter and it's value");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"param2" value:@"value2" urlString:@"scheme://host:12345/path?param1=value1"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path?param1=value1&param2=value2", @"expected url with with two parameters plus value");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"umlautParam" value:@"välüe1" urlString:@"scheme://host:12345/path"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path?umlautParam=v%C3%A4l%C3%BCe1", @"expected url with with encoded value");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:nil value:@"paramIsNil" urlString:@"scheme://host:12345/path"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path", @"expected url not to be modified as parameter is nil");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"valueIsNil" value:nil urlString:@"scheme://host:12345/path"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path", @"expected url not to be modified as value is nil");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"param1" value:@"value1" urlString:@"scheme://host/"];
+    XCTAssertEqualObjects(path, @"scheme://host/?param1=value1", @"expected url (no port) with with one parameter and it's value");
+    
+    path = [CMISURLUtil urlStringByAppendingParameter:@"param1" value:@"value1" urlString:@"https://example.com:12345/path1/path2"];
+    XCTAssertEqualObjects(path, @"https://example.com:12345/path1/path2?param1=value1", @"expected url with with one parameter and it's value");
+}
+
+-(void)testUrlUtilAppendPath
+{
+    NSString *path;
+    
+    path = [CMISURLUtil urlStringByAppendingPath:@"aPath" urlString:@"scheme://host:12345?"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/aPath?", @"expected url with path");
+    
+    path = [CMISURLUtil urlStringByAppendingPath:@"subPath" urlString:@"scheme://host:12345/path?"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path/subPath?", @"expected url with sub path component");
+    
+    path = [CMISURLUtil urlStringByAppendingPath:@"subPath" urlString:@"scheme://host:12345/path"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path/subPath", @"expected url with sub path component");
+    
+    path = [CMISURLUtil urlStringByAppendingPath:@"subPath" urlString:@"scheme://host:12345/path/"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path/subPath", @"expected url with sub path component");
+    
+    path = [CMISURLUtil urlStringByAppendingPath:@"subPath" urlString:@"scheme://host:12345/path?parm1=value1"];
+    XCTAssertEqualObjects(path, @"scheme://host:12345/path/subPath?parm1=value1", @"expected url with sub path component, parmater and it's value");
+}
+
 @end