This commit is contained in:
Ludovic Marcotte
2014-05-27 14:44:57 -04:00
parent 6bab4c94f2
commit d35c52bb38
8 changed files with 387 additions and 74 deletions
+2
View File
@@ -84,6 +84,8 @@ typedef enum {
- (NSArray *) allFolderPaths;
- (NSArray *) allFoldersMetadata;
- (NSDictionary *) imapFolderGUIDs;
- (BOOL) isInDraftsFolder;
/* special folders */
+67
View File
@@ -60,6 +60,8 @@
#import "SOGoUser+Mailer.h"
#import "SOGoMailAccount.h"
#import <Foundation/NSProcessInfo.h>
#define XMLNS_INVERSEDAV @"urn:inverse:params:xml:ns:inverse-dav"
@@ -659,6 +661,71 @@ static NSString *inboxFolderName = @"INBOX";
return password;
}
- (NSDictionary *) imapFolderGUIDs
{
NSDictionary *result, *nresult, *folderData;
NSMutableDictionary *folders;
NGImap4Client *client;
SOGoUserDefaults *ud;
NSArray *folderList;
NSEnumerator *e;
NSString *guid;
id object;
BOOL subscribedOnly;
ud = [[context activeUser] userDefaults];
subscribedOnly = [ud mailShowSubscribedFoldersOnly];
folderList = [[self imap4Connection] allFoldersForURL: [self imap4URL]
onlySubscribedFolders: subscribedOnly];
folders = [NSMutableDictionary dictionary];
client = [[self imap4Connection] client];
result = [client annotation: @"*" entryName: @"/comment" attributeName: @"value.priv"];
if (![[result objectForKey: @"result"] boolValue])
{
NSLog(@"IMAP annotation call failed.");
return folders;
}
e = [folderList objectEnumerator];
while (object = [e nextObject])
{
guid = [[[[result objectForKey: @"FolderList"] objectForKey: [object substringFromIndex: 1]] objectForKey: @"/comment"] objectForKey: @"value.priv"];
if (!guid)
{
guid = [[NSProcessInfo processInfo] globallyUniqueString];
nresult = [client annotation: [object substringFromIndex: 1] entryName: @"/comment" attributeName: @"value.priv" attributeValue: guid];
if (![[nresult objectForKey: @"result"] boolValue])
{
// need to implement X-GUID query for Dovecot - this requires modification in SOPE to support following command:
// 1 list "" "*" return (status (x-guid)) -> this would avoid firing a command per folder to IMAP
//guid = [NSString stringWithFormat: @"%@-%@", [object substringFromIndex: 1], @"xxx" ];
nresult = [client status: [object substringFromIndex: 1] flags: [NSArray arrayWithObject: @"x-guid"]];
guid = [nresult objectForKey: @"x-guid"];
if (!guid)
{
guid = [NSString stringWithFormat: @"%@", [object substringFromIndex: 1]];
}
NSLog(@"tfu setannotation failed: %@", nresult );
NSLog(@"tfu uniqueid folderid: %@", guid );
}
}
[folders setObject: guid forKey: [object substringFromIndex: 1]];
}
return folders;
}
/* name lookup */
- (id) lookupName: (NSString *) _key
+3
View File
@@ -67,6 +67,9 @@ typedef enum {
- (NSDictionary *) lookupRecord: (NSString *) path
newerThanVersion: (NSInteger) startVersion;
- (NSArray *) folderList: (NSString *) deviceId
newerThanVersion: (NSInteger) startVersion;
- (void) setObjectType: (SOGoCacheObjectType) newObjectType;
- (SOGoCacheObjectType) objectType; /* message, fai, folder */
+48 -7
View File
@@ -112,7 +112,7 @@ static EOAttribute *textColumn = nil;
tableUrl = [container tableUrl];
[tableUrl retain];
if (!tableUrl)
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"table url is not set for object '%@'", self];
}
@@ -169,7 +169,7 @@ static EOAttribute *textColumn = nil;
path = [NSMutableString stringWithFormat: @"/%@", nameInContainer];
if ([path rangeOfString: @"//"].location != NSNotFound)
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"object path has not been properly set for"
" folder '%@' (%@)",
self, path];
@@ -190,7 +190,7 @@ static EOAttribute *textColumn = nil;
- (NSCalendarDate *) creationDate
{
if (!initialized)
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"record has not been initialized: %@", self];
return creationDate;
@@ -199,7 +199,7 @@ static EOAttribute *textColumn = nil;
- (NSCalendarDate *) lastModified
{
if (!initialized)
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"record has not been initialized: %@", self];
return lastModified;
@@ -350,7 +350,7 @@ static EOAttribute *textColumn = nil;
EOAdaptor *adaptor;
if ([path hasSuffix: @"/"])
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"path ends with a slash: %@", path];
tableName = [self tableName];
@@ -375,6 +375,47 @@ static EOAttribute *textColumn = nil;
return record;
}
// get a list of all folders
- (NSArray *) folderList: (NSString *) deviceId
newerThanVersion: (NSInteger) startVersion
{
NSMutableArray *recordsOut;
NSArray *records;
NSString *tableName, *pathValue;
NSMutableString *sql;
EOAdaptor *adaptor;
NSUInteger count, max;
if ([deviceId hasSuffix: @"/"])
[NSException raise: @"SOGoCacheIOException"
format: @"path ends with a slash: %@", deviceId];
tableName = [self tableName];
adaptor = [self tableChannelAdaptor];
pathValue = [adaptor formatValue: [NSString stringWithFormat: @"/%@+folder%", deviceId]
forAttribute: textColumn];
/* query */
sql = [NSMutableString stringWithFormat:
@"SELECT * FROM %@ WHERE c_path LIKE %@ AND c_deleted <> 1",
tableName, pathValue];
if (startVersion > -1)
[sql appendFormat: @" AND c_version > %d", startVersion];
/* execution */
records = [self performSQLQuery: sql];
max = [records count];
recordsOut = [[NSMutableArray alloc] init];
for (count = 0; count < max; count++)
{
[recordsOut addObject: [[records objectAtIndex: count] objectForKey: @"c_path"]];
}
return recordsOut;
}
- (void) reloadIfNeeded
{
/* if object is uninitialized: reload without condition, otherwise, load if
@@ -428,7 +469,7 @@ static EOAttribute *textColumn = nil;
NSException *result;
if (!initialized)
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"record has not been initialized: %@", self];
cm = [GCSChannelManager defaultChannelManager];
@@ -447,7 +488,7 @@ static EOAttribute *textColumn = nil;
lastModifiedValue = (NSInteger) [lastModified timeIntervalSince1970];
if (objectType == -1)
[NSException raise: @"MAPIStoreIOException"
[NSException raise: @"SOGoCacheIOException"
format: @"object type has not been set for object '%@'",
self];