diff --git a/ChangeLog b/ChangeLog index 06e7395e8..9688ec155 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,19 @@ 2009-06-03 Wolfgang Sourdeau + * SoObjects/SOGo/SOGoGCSFolder.m + (-initializeQuickTablesAclsInContext:): new method that + initializes the new "userCanAccessAllObjects" ivar. + + * SoObjects/Appointments/SOGoAppointmentFolder.m + (-initWithName:inContainer:): added new + "userCanAccessObjectsClassifiedAs" ivar (array of bools) to + quickly determine whether a user can access a component + informations. + (-initializeQuickTablesAclsInContext:): new method that + initializes the new ivar above. + (-davCalendarQuery:, -davCalendarMultiget:): invoke the new method + above. + * Main/NSException+Stacktrace.m, SOPE/NGCards/NGCardsSaxHandler.m, SOPE/NGCards/NSString+NGCards.m, SOPE/NGCards/versitCardsSaxDriver/VSSaxDriver.m, diff --git a/SOPE/NGCards/iCalEntityObject.h b/SOPE/NGCards/iCalEntityObject.h index 870d9acc2..d9d7faf6d 100644 --- a/SOPE/NGCards/iCalEntityObject.h +++ b/SOPE/NGCards/iCalEntityObject.h @@ -40,6 +40,7 @@ typedef enum iCalAccessPublic = 0, iCalAccessPrivate = 1, iCalAccessConfidential = 2, + iCalAccessClassCount = 3 } iCalAccessClass; @interface iCalEntityObject : CardGroup diff --git a/SoObjects/Appointments/SOGoAppointmentFolder.h b/SoObjects/Appointments/SOGoAppointmentFolder.h index 7c0f3f9ce..a5cad1562 100644 --- a/SoObjects/Appointments/SOGoAppointmentFolder.h +++ b/SoObjects/Appointments/SOGoAppointmentFolder.h @@ -55,6 +55,7 @@ NSMutableDictionary *uidToFilename; NSMutableDictionary *aclMatrix; NSMutableArray *stripFields; + BOOL userCanAccessObjectsClassifiedAs[iCalAccessClassCount]; } - (BOOL) isActive; diff --git a/SoObjects/Appointments/SOGoAppointmentFolder.m b/SoObjects/Appointments/SOGoAppointmentFolder.m index a4e7c03fd..085a17141 100644 --- a/SoObjects/Appointments/SOGoAppointmentFolder.m +++ b/SoObjects/Appointments/SOGoAppointmentFolder.m @@ -30,7 +30,6 @@ #import #import -#import #import #import #import @@ -259,6 +258,8 @@ static NSArray *reducedReportQueryFields = nil; aclMatrix = [NSMutableDictionary new]; stripFields = nil; uidToFilename = nil; + memset (userCanAccessObjectsClassifiedAs, NO, + iCalAccessClassCount * sizeof (BOOL)); } return self; @@ -1091,31 +1092,26 @@ firstInstanceCalendarDateRange: (NGCalendarDateRange *) fir SOGoCalendarComponent *sogoObject; NSString **currentProperty; NSString **values, **currentValue; - SoSecurityManager *mgr; SEL methodSel; - - values = NSZoneMalloc (NULL, - (propertiesCount + 1) * sizeof (NSMutableString *)); - *(values + propertiesCount) = nil; + iCalAccessClass classification; // NSLog (@"_properties:ofObject:: %@", [NSDate date]); -#warning this check should be done directly in the query... we should fix this sometime - mgr = [SoSecurityManager sharedSecurityManager]; + values = NSZoneMalloc (NULL, + (propertiesCount + 1) * sizeof (NSString *)); + *(values + propertiesCount) = nil; + classification = [[object objectForKey: @"c_classification"] intValue]; //c = [self objectClassForComponentName: [object objectForKey: @"c_component"]]; - sogoObject = [SOGoCalendarComponent objectWithRecord: object - inContainer: self]; - [sogoObject setComponentTag: [object objectForKey: @"c_component"]]; - //sogoObject = [self _createChildComponentWithRecord: object]; - - if (activeUserIsOwner - || [[self ownerInContext: context] - isEqualToString: [[context activeUser] login]] - || !([mgr validatePermission: SOGoPerm_AccessObject - onObject: sogoObject - inContext: context])) + if (userCanAccessObjectsClassifiedAs[classification]) { + #warning TODO: determine why this commented invocation takes so long... + // sogoObject = [self _createChildComponentWithRecord: object]; + + sogoObject = [SOGoCalendarComponent objectWithRecord: object + inContainer: self]; + [sogoObject setComponentTag: [object objectForKey: @"c_component"]]; + currentProperty = properties; currentValue = values; while (*currentProperty) @@ -1154,7 +1150,8 @@ firstInstanceCalendarDateRange: (NGCalendarDateRange *) fir properties200 = [NSMutableArray new]; properties404 = [NSMutableArray new]; - values = [self _properties: properties count: propertiesCount ofObject: object]; + values = [self _properties: properties count: propertiesCount + ofObject: object]; currentValue = values; property = properties; @@ -1650,7 +1647,7 @@ firstInstanceCalendarDateRange: (NGCalendarDateRange *) fir additionalFilters: additionalFilters]; //NSLog(@"adding properties"); max = [apts count]; - buffer = [[NSMutableString alloc] initWithCapacity: max*512]; + buffer = [[NSMutableString alloc] initWithCapacity: max * 512]; for (count = 0; count < max; count++) [self appendObject: [apts objectAtIndex: count] properties: properties @@ -1671,6 +1668,8 @@ firstInstanceCalendarDateRange: (NGCalendarDateRange *) fir id document; id documentElement; + [self initializeQuickTablesAclsInContext: queryContext]; + r = [context response]; [r setStatus: 207]; [r setContentEncoding: NSUTF8StringEncoding]; @@ -1874,6 +1873,8 @@ firstInstanceCalendarDateRange: (NGCalendarDateRange *) fir id document; id documentElement; + [self initializeQuickTablesAclsInContext: queryContext]; + r = [context response]; [r setStatus: 207]; [r setContentEncoding: NSUTF8StringEncoding]; @@ -2377,6 +2378,41 @@ firstInstanceCalendarDateRange: (NGCalendarDateRange *) fir return accessRole; } +- (void) initializeQuickTablesAclsInContext: (WOContext *) localContext +{ + NSString *login, *role, *permission; + iCalAccessClass currentClass; + unsigned int permStrIndex; + + [super initializeQuickTablesAclsInContext: localContext]; + /* We assume "userIsOwner" will be set after calling the super method. */ + if (!activeUserIsOwner) + { + login = [[localContext activeUser] login]; + permStrIndex = [@"Component" length]; + } + + for (currentClass = 0; currentClass < iCalAccessClassCount; currentClass++) + { + if (activeUserIsOwner) + userCanAccessObjectsClassifiedAs[currentClass] = YES; + else + { + role = [self roleForComponentsWithAccessClass: currentClass + forUser: login]; + if ([role length]) + { + permission = [role substringFromIndex: permStrIndex]; + userCanAccessObjectsClassifiedAs[currentClass] + = ([permission isEqualToString: @"Viewer"] + || [permission isEqualToString: @"DAndTViewer"] + || [permission isEqualToString: @"Modifier"] + || [permission isEqualToString: @"Responder"]); + } + } + } +} + - (NSArray *) fetchFreeBusyInfosFrom: (NSCalendarDate *) _startDate to: (NSCalendarDate *) _endDate { diff --git a/SoObjects/SOGo/SOGoGCSFolder.h b/SoObjects/SOGo/SOGoGCSFolder.h index e3fe35b8c..fb4f7fbc9 100644 --- a/SoObjects/SOGo/SOGoGCSFolder.h +++ b/SoObjects/SOGo/SOGoGCSFolder.h @@ -49,6 +49,8 @@ GCSFolder *ocsFolder; NSMutableDictionary *childRecords; NSMutableDictionary *aclCache; + BOOL userCanAccessAllObjects; /* i.e. user obtains 'Access Object' on + subobjects */ } + (id) folderWithSubscriptionReference: (NSString *) reference @@ -88,6 +90,8 @@ fromMailInvitation: (BOOL) isMailInvitation inContext: (WOContext *) localContext; +- (void) initializeQuickTablesAclsInContext: (WOContext *) localContext; + /* acls as a container */ - (NSArray *) aclUsersForObjectAtPath: (NSArray *) objectPathArray; - (NSArray *) aclsForUser: (NSString *) uid diff --git a/SoObjects/SOGo/SOGoGCSFolder.m b/SoObjects/SOGo/SOGoGCSFolder.m index c2776fff8..7c665f1e4 100644 --- a/SoObjects/SOGo/SOGoGCSFolder.m +++ b/SoObjects/SOGo/SOGoGCSFolder.m @@ -185,6 +185,7 @@ static NSArray *childRecordFields = nil; ocsFolder = nil; aclCache = [NSMutableDictionary new]; childRecords = [NSMutableDictionary new]; + userCanAccessAllObjects = NO; } return self; @@ -756,6 +757,26 @@ static NSArray *childRecordFields = nil; inContext: queryContext]; } +/* handling acls from quick tables */ +- (void) initializeQuickTablesAclsInContext: (WOContext *) localContext +{ + NSString *login; + + if (activeUserIsOwner) + userCanAccessAllObjects = activeUserIsOwner; + else + { + login = [[localContext activeUser] login]; + /* we only grant "userCanAccessAllObjects" for role "ObjectEraser" and + not "ObjectCreator" because the latter doesn't imply we can read + properties from subobjects or even know their existence. */ + userCanAccessAllObjects = ([[self ownerInContext: localContext] + isEqualToString: login] + || [[self aclsForUser: login] + containsObject: SOGoRole_ObjectEraser]); + } +} + /* acls as a container */ - (NSArray *) aclUsersForObjectAtPath: (NSArray *) objectPathArray;