mirror of
https://github.com/inverse-inc/sogo.git
synced 2026-02-17 07:33:57 +00:00
First pass at 'push' support for Ping and Sync
This commit is contained in:
@@ -104,6 +104,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
#include "SOGoActiveSyncConstants.h"
|
||||
#include "SOGoMailObject+ActiveSync.h"
|
||||
|
||||
#include <unistd.h>
|
||||
|
||||
@implementation SOGoActiveSyncDispatcher (Sync)
|
||||
|
||||
//
|
||||
@@ -635,6 +637,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
//
|
||||
- (void) processSyncCollection: (id <DOMElement>) theDocumentElement
|
||||
inBuffer: (NSMutableString *) theBuffer
|
||||
changeDetected: (BOOL *) changeDetected
|
||||
{
|
||||
NSString *collectionId, *realCollectionId, *syncKey, *davCollectionTag, *bodyPreferenceType;
|
||||
SOGoMicrosoftActiveSyncFolderType folderType;
|
||||
@@ -666,6 +669,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
{
|
||||
davCollectionTag = @"-1";
|
||||
first_sync = YES;
|
||||
*changeDetected = YES;
|
||||
}
|
||||
|
||||
// We check our sync preferences and we stash them
|
||||
@@ -716,7 +720,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
// If we got any changes or if we have applied any commands
|
||||
// let's regenerate our SyncKey based on the collection tag.
|
||||
if ([changeBuffer length] || [commandsBuffer length])
|
||||
davCollectionTag = [collection davCollectionTag];
|
||||
{
|
||||
davCollectionTag = [collection davCollectionTag];
|
||||
*changeDetected = YES;
|
||||
}
|
||||
|
||||
// Generate the response buffer
|
||||
[theBuffer appendString: @"<Collection>"];
|
||||
@@ -840,30 +847,67 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
{
|
||||
id <DOMElement> aCollection;
|
||||
NSArray *allCollections;
|
||||
NSMutableString *s;
|
||||
NSMutableString *output, *s;
|
||||
NSData *d;
|
||||
|
||||
int i;
|
||||
int i, j, heartbeatInterval;
|
||||
BOOL changeDetected;
|
||||
|
||||
// We initialize our output buffer
|
||||
s = [NSMutableString string];
|
||||
output = [NSMutableString string];
|
||||
|
||||
[s appendString: @"<?xml version=\"1.0\" encoding=\"utf-8\"?>"];
|
||||
[s appendString: @"<!DOCTYPE ActiveSync PUBLIC \"-//MICROSOFT//DTD ActiveSync//EN\" \"http://www.microsoft.com/\">"];
|
||||
[s appendString: @"<Sync xmlns=\"AirSync:\"><Collections>"];
|
||||
[output appendString: @"<?xml version=\"1.0\" encoding=\"utf-8\"?>"];
|
||||
[output appendString: @"<!DOCTYPE ActiveSync PUBLIC \"-//MICROSOFT//DTD ActiveSync//EN\" \"http://www.microsoft.com/\">"];
|
||||
[output appendString: @"<Sync xmlns=\"AirSync:\">"];
|
||||
|
||||
allCollections = (id)[theDocumentElement getElementsByTagName: @"Collection"];
|
||||
heartbeatInterval = [[[(id)[theDocumentElement getElementsByTagName: @"HeartbeatInterval"] lastObject] textValue] intValue];
|
||||
|
||||
for (i = 0; i < [allCollections count]; i++)
|
||||
// We check to see if our heartbeat interval falls into the supported ranges.
|
||||
if (heartbeatInterval > 300 || heartbeatInterval < 1)
|
||||
{
|
||||
aCollection = [allCollections objectAtIndex: i];
|
||||
// Interval is too long, inform the client.
|
||||
heartbeatInterval = 300;
|
||||
|
||||
[self processSyncCollection: aCollection inBuffer: s];
|
||||
//[output appendFormat: @"<Limit>%d</Limit>", 300];
|
||||
//[output appendFormat: @"<Status>%d</Status>", 14];
|
||||
//[output appendString: @"</Sync>"];
|
||||
//d = [[output dataUsingEncoding: NSUTF8StringEncoding] xml2wbxml];
|
||||
//[theResponse setContent: d];
|
||||
//return;
|
||||
}
|
||||
|
||||
[s appendString: @"</Collections></Sync>"];
|
||||
[output appendString: @"<Collections>"];
|
||||
|
||||
allCollections = (id)[theDocumentElement getElementsByTagName: @"Collection"];
|
||||
|
||||
// We enter our loop detection change
|
||||
for (i = 0; i < (heartbeatInterval/60); i++)
|
||||
{
|
||||
s = [NSMutableString string];
|
||||
|
||||
for (j = 0; j < [allCollections count]; j++)
|
||||
{
|
||||
aCollection = [allCollections objectAtIndex: j];
|
||||
|
||||
[self processSyncCollection: aCollection inBuffer: s changeDetected: &changeDetected];
|
||||
}
|
||||
|
||||
if (changeDetected)
|
||||
{
|
||||
NSLog(@"Change detected, we push the content.");
|
||||
[output appendString: s];
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
NSLog(@"Sleeping 60 seconds while detecting changes...");
|
||||
sleep(60);
|
||||
}
|
||||
}
|
||||
|
||||
[output appendString: @"</Collections></Sync>"];
|
||||
|
||||
d = [[s dataUsingEncoding: NSUTF8StringEncoding] xml2wbxml];
|
||||
d = [[output dataUsingEncoding: NSUTF8StringEncoding] xml2wbxml];
|
||||
|
||||
[theResponse setContent: d];
|
||||
}
|
||||
|
||||
@@ -112,6 +112,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
#include "SOGoActiveSyncConstants.h"
|
||||
#include "SOGoMailObject+ActiveSync.h"
|
||||
|
||||
#include <unistd.h>
|
||||
|
||||
@implementation SOGoActiveSyncDispatcher
|
||||
|
||||
- (void) _setFolderSyncKey: (NSString *) theSyncKey
|
||||
@@ -599,7 +601,6 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
@"deleted"];
|
||||
sinceDateQualifier = [EOQualifier qualifierWithQualifierFormat:
|
||||
@"(DATE >= %@)", filter];
|
||||
|
||||
|
||||
qualifier = [[EOAndQualifier alloc] initWithQualifiers: notDeletedQualifier, sinceDateQualifier,
|
||||
nil];
|
||||
@@ -614,7 +615,6 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
[s appendString: @"<!DOCTYPE ActiveSync PUBLIC \"-//MICROSOFT//DTD ActiveSync//EN\" \"http://www.microsoft.com/\">"];
|
||||
[s appendFormat: @"<GetItemEstimate xmlns=\"GetItemEstimate:\"><Response><Status>%d</Status><Collection>", status];
|
||||
|
||||
[s appendString: @"<Class>Email</Class>"];
|
||||
[s appendFormat: @"<CollectionId>%@</CollectionId>", collectionId];
|
||||
[s appendFormat: @"<Estimate>%d</Estimate>", [uids count]];
|
||||
|
||||
@@ -623,7 +623,6 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
d = [[s dataUsingEncoding: NSUTF8StringEncoding] xml2wbxml];
|
||||
|
||||
[theResponse setContent: d];
|
||||
|
||||
}
|
||||
|
||||
//
|
||||
@@ -900,7 +899,12 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
}
|
||||
|
||||
//
|
||||
// We ignore everything for now
|
||||
// Ping requests make a little sense because the request
|
||||
// doesn't contain the SyncKey on the client. So we can't
|
||||
// really know if something has changed on the server. What we
|
||||
// do for now is simply return Status=5 with the HeartbeatInterval
|
||||
// set at 60 seconds or we wait 60 seconds before responding with
|
||||
// Status=1
|
||||
//
|
||||
- (void) processPing: (id <DOMElement>) theDocumentElement
|
||||
inResponse: (WOResponse *) theResponse
|
||||
@@ -908,11 +912,37 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
NSMutableString *s;
|
||||
NSData *d;
|
||||
|
||||
int heartbeatInterval, status;
|
||||
|
||||
if (theDocumentElement)
|
||||
heartbeatInterval = [[[(id)[theDocumentElement getElementsByTagName: @"HeartbeatInterval"] lastObject] textValue] intValue];
|
||||
else
|
||||
heartbeatInterval = 60;
|
||||
|
||||
if (heartbeatInterval > 60 || heartbeatInterval == 0)
|
||||
{
|
||||
heartbeatInterval = 60;
|
||||
status = 5;
|
||||
}
|
||||
else
|
||||
{
|
||||
NSLog(@"Got Ping request with valid interval - sleeping for 60 seconds.");
|
||||
sleep(60);
|
||||
status = 1;
|
||||
}
|
||||
|
||||
// We generate our response
|
||||
s = [NSMutableString string];
|
||||
[s appendString: @"<?xml version=\"1.0\" encoding=\"utf-8\"?>"];
|
||||
[s appendString: @"<!DOCTYPE ActiveSync PUBLIC \"-//MICROSOFT//DTD ActiveSync//EN\" \"http://www.microsoft.com/\">"];
|
||||
[s appendString: @"<Ping xmlns=\"Ping:\">"];
|
||||
[s appendFormat: @"<Status>1</Status>"];
|
||||
[s appendFormat: @"<Status>%d</Status>", status];
|
||||
|
||||
if (status == 5)
|
||||
{
|
||||
[s appendFormat: @"<HeartbeatInterval>%d</HeartbeatInterval>", heartbeatInterval];
|
||||
}
|
||||
|
||||
[s appendString: @"</Ping>"];
|
||||
|
||||
d = [[s dataUsingEncoding: NSUTF8StringEncoding] xml2wbxml];
|
||||
@@ -1432,6 +1462,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
[context setObject: deviceId forKey: @"DeviceId"];
|
||||
|
||||
d = [[theRequest content] wbxml2xml];
|
||||
documentElement = nil;
|
||||
|
||||
if (!d)
|
||||
{
|
||||
|
||||
@@ -44,8 +44,10 @@ ProxyPass /SOGo http://127.0.0.1:20000/SOGo retry=0
|
||||
|
||||
#
|
||||
# Enable to use Microsoft Active Sync support
|
||||
# Note that you MUST have many sogod workers to use Active Sync.
|
||||
# See the SOGo Installation and Configuration guide for more details.
|
||||
#
|
||||
#ProxyPass /Microsoft-Server-ActiveSync http://127.0.0.1:20000/SOGo/Microsoft-Server-ActiveSync retry=0
|
||||
#ProxyPass /Microsoft-Server-ActiveSync http://127.0.0.1:20000/SOGo/Microsoft-Server-ActiveSync retry=60 connectiontimeout=5 timeout=360
|
||||
|
||||
<Proxy http://127.0.0.1:20000/SOGo>
|
||||
## adjust the following to your configuration
|
||||
|
||||
Reference in New Issue
Block a user