Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Add objective-c gdata client dep, enable creation of target calendar …

…on Google calendar
  • Loading branch information...
commit d8f2af7e944a3f076eff50622a4cb7e3d70d1bcd 1 parent 8ca9ff2
Nathan Parry authored
3  .gitmodules
View
@@ -0,0 +1,3 @@
+[submodule "external/gdata"]
+ path = external/gdata
+ url = git@github.com:nparry/gdata-objectivec-client.git
103 BirthdaySync.xcodeproj/project.pbxproj
View
@@ -8,6 +8,8 @@
/* Begin PBXBuildFile section */
1DDD58160DA1D0A300B32029 /* MainMenu.xib in Resources */ = {isa = PBXBuildFile; fileRef = 1DDD58140DA1D0A300B32029 /* MainMenu.xib */; };
+ 454E2E0C0F6DC72B009098E3 /* GData.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 454E2E070F6DC71A009098E3 /* GData.framework */; };
+ 454E2F050F6DE5B5009098E3 /* GData.framework in CopyFiles */ = {isa = PBXBuildFile; fileRef = 454E2E070F6DC71A009098E3 /* GData.framework */; };
45FC24620F5AE792009B70E3 /* AppController.m in Sources */ = {isa = PBXBuildFile; fileRef = 45FC24610F5AE792009B70E3 /* AppController.m */; };
45FE574C0F5B16E900CC771D /* PasswordStorage.m in Sources */ = {isa = PBXBuildFile; fileRef = 45FE574B0F5B16E900CC771D /* PasswordStorage.m */; };
45FE57680F5B26B400CC771D /* Security.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 45FE57670F5B26B400CC771D /* Security.framework */; };
@@ -20,6 +22,50 @@
8D11072F0486CEB800E47090 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 1058C7A1FEA54F0111CA2CBB /* Cocoa.framework */; };
/* End PBXBuildFile section */
+/* Begin PBXContainerItemProxy section */
+ 454E2E060F6DC71A009098E3 /* PBXContainerItemProxy */ = {
+ isa = PBXContainerItemProxy;
+ containerPortal = 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */;
+ proxyType = 2;
+ remoteGlobalIDString = 4F38F6A60B66E91D00B24B81;
+ remoteInfo = GDataFramework;
+ };
+ 454E2E080F6DC71A009098E3 /* PBXContainerItemProxy */ = {
+ isa = PBXContainerItemProxy;
+ containerPortal = 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */;
+ proxyType = 2;
+ remoteGlobalIDString = 4F14A9DD0B1276B70072EBB8;
+ remoteInfo = GDataUnitTests;
+ };
+ 454E2E0A0F6DC71A009098E3 /* PBXContainerItemProxy */ = {
+ isa = PBXContainerItemProxy;
+ containerPortal = 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */;
+ proxyType = 2;
+ remoteGlobalIDString = 4F1AD9020B71603F00DC0485;
+ remoteInfo = DevelopmentTestTool;
+ };
+ 454E2E0D0F6DC737009098E3 /* PBXContainerItemProxy */ = {
+ isa = PBXContainerItemProxy;
+ containerPortal = 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */;
+ proxyType = 1;
+ remoteGlobalIDString = 4F38F6A50B66E91D00B24B81;
+ remoteInfo = GDataFramework;
+ };
+/* End PBXContainerItemProxy section */
+
+/* Begin PBXCopyFilesBuildPhase section */
+ 454E2F090F6DE5BE009098E3 /* CopyFiles */ = {
+ isa = PBXCopyFilesBuildPhase;
+ buildActionMask = 2147483647;
+ dstPath = "";
+ dstSubfolderSpec = 10;
+ files = (
+ 454E2F050F6DE5B5009098E3 /* GData.framework in CopyFiles */,
+ );
+ runOnlyForDeploymentPostprocessing = 0;
+ };
+/* End PBXCopyFilesBuildPhase section */
+
/* Begin PBXFileReference section */
089C165DFE840E0CC02AAC07 /* English */ = {isa = PBXFileReference; fileEncoding = 10; lastKnownFileType = text.plist.strings; name = English; path = English.lproj/InfoPlist.strings; sourceTree = "<group>"; };
1058C7A1FEA54F0111CA2CBB /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = /System/Library/Frameworks/Cocoa.framework; sourceTree = "<absolute>"; };
@@ -29,6 +75,7 @@
29B97324FDCFA39411CA2CEA /* AppKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AppKit.framework; path = /System/Library/Frameworks/AppKit.framework; sourceTree = "<absolute>"; };
29B97325FDCFA39411CA2CEA /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = /System/Library/Frameworks/Foundation.framework; sourceTree = "<absolute>"; };
32CA4F630368D1EE00C91783 /* BirthdaySync_Prefix.pch */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = BirthdaySync_Prefix.pch; sourceTree = "<group>"; };
+ 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = GData.xcodeproj; path = external/gdata/Source/GData.xcodeproj; sourceTree = "<group>"; };
45FC24600F5AE792009B70E3 /* AppController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AppController.h; sourceTree = "<group>"; };
45FC24610F5AE792009B70E3 /* AppController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AppController.m; sourceTree = "<group>"; };
45FE574A0F5B16E900CC771D /* PasswordStorage.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PasswordStorage.h; sourceTree = "<group>"; };
@@ -49,6 +96,7 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
+ 454E2E0C0F6DC72B009098E3 /* GData.framework in Frameworks */,
8D11072F0486CEB800E47090 /* Cocoa.framework in Frameworks */,
45FE57680F5B26B400CC771D /* Security.framework in Frameworks */,
45FE5A750F5B8C1B00CC771D /* SyncServices.framework in Frameworks */,
@@ -102,6 +150,7 @@
29B97314FDCFA39411CA2CEA /* BirthdaySync */ = {
isa = PBXGroup;
children = (
+ 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */,
080E96DDFE201D6D7F000001 /* Classes */,
29B97315FDCFA39411CA2CEA /* Other Sources */,
29B97317FDCFA39411CA2CEA /* Resources */,
@@ -142,6 +191,16 @@
name = Frameworks;
sourceTree = "<group>";
};
+ 454E2DFD0F6DC719009098E3 /* Products */ = {
+ isa = PBXGroup;
+ children = (
+ 454E2E070F6DC71A009098E3 /* GData.framework */,
+ 454E2E090F6DC71A009098E3 /* GDataUnitTests.octest */,
+ 454E2E0B0F6DC71A009098E3 /* DevelopmentTestTool */,
+ );
+ name = Products;
+ sourceTree = "<group>";
+ };
/* End PBXGroup section */
/* Begin PBXNativeTarget section */
@@ -152,10 +211,12 @@
8D1107290486CEB800E47090 /* Resources */,
8D11072C0486CEB800E47090 /* Sources */,
8D11072E0486CEB800E47090 /* Frameworks */,
+ 454E2F090F6DE5BE009098E3 /* CopyFiles */,
);
buildRules = (
);
dependencies = (
+ 454E2E0E0F6DC737009098E3 /* PBXTargetDependency */,
);
name = BirthdaySync;
productInstallPath = "$(HOME)/Applications";
@@ -173,6 +234,12 @@
hasScannedForEncodings = 1;
mainGroup = 29B97314FDCFA39411CA2CEA /* BirthdaySync */;
projectDirPath = "";
+ projectReferences = (
+ {
+ ProductGroup = 454E2DFD0F6DC719009098E3 /* Products */;
+ ProjectRef = 454E2DFC0F6DC719009098E3 /* GData.xcodeproj */;
+ },
+ );
projectRoot = "";
targets = (
8D1107260486CEB800E47090 /* BirthdaySync */,
@@ -180,6 +247,30 @@
};
/* End PBXProject section */
+/* Begin PBXReferenceProxy section */
+ 454E2E070F6DC71A009098E3 /* GData.framework */ = {
+ isa = PBXReferenceProxy;
+ fileType = wrapper.framework;
+ path = GData.framework;
+ remoteRef = 454E2E060F6DC71A009098E3 /* PBXContainerItemProxy */;
+ sourceTree = BUILT_PRODUCTS_DIR;
+ };
+ 454E2E090F6DC71A009098E3 /* GDataUnitTests.octest */ = {
+ isa = PBXReferenceProxy;
+ fileType = wrapper.cfbundle;
+ path = GDataUnitTests.octest;
+ remoteRef = 454E2E080F6DC71A009098E3 /* PBXContainerItemProxy */;
+ sourceTree = BUILT_PRODUCTS_DIR;
+ };
+ 454E2E0B0F6DC71A009098E3 /* DevelopmentTestTool */ = {
+ isa = PBXReferenceProxy;
+ fileType = "compiled.mach-o.executable";
+ path = DevelopmentTestTool;
+ remoteRef = 454E2E0A0F6DC71A009098E3 /* PBXContainerItemProxy */;
+ sourceTree = BUILT_PRODUCTS_DIR;
+ };
+/* End PBXReferenceProxy section */
+
/* Begin PBXResourcesBuildPhase section */
8D1107290486CEB800E47090 /* Resources */ = {
isa = PBXResourcesBuildPhase;
@@ -208,6 +299,14 @@
};
/* End PBXSourcesBuildPhase section */
+/* Begin PBXTargetDependency section */
+ 454E2E0E0F6DC737009098E3 /* PBXTargetDependency */ = {
+ isa = PBXTargetDependency;
+ name = GDataFramework;
+ targetProxy = 454E2E0D0F6DC737009098E3 /* PBXContainerItemProxy */;
+ };
+/* End PBXTargetDependency section */
+
/* Begin PBXVariantGroup section */
089C165CFE840E0CC02AAC07 /* InfoPlist.strings */ = {
isa = PBXVariantGroup;
@@ -263,10 +362,12 @@
isa = XCBuildConfiguration;
buildSettings = {
ARCHS = "$(ARCHS_STANDARD_32_BIT)";
+ FRAMEWORK_SEARCH_PATHS = "${SRCROOT}/external/gdata/Source/build/${CONFIGURATION}";
GCC_C_LANGUAGE_STANDARD = c99;
GCC_OPTIMIZATION_LEVEL = 0;
GCC_WARN_ABOUT_RETURN_TYPE = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
+ HEADER_SEARCH_PATHS = "${SRCROOT}/external/gdata/Source/build/${CONFIGURATION}/GData.framework/Headers";
ONLY_ACTIVE_ARCH = YES;
PREBINDING = NO;
SDKROOT = macosx10.5;
@@ -277,9 +378,11 @@
isa = XCBuildConfiguration;
buildSettings = {
ARCHS = "$(ARCHS_STANDARD_32_BIT)";
+ FRAMEWORK_SEARCH_PATHS = "${SRCROOT}/external/gdata/Source/build/${CONFIGURATION}";
GCC_C_LANGUAGE_STANDARD = c99;
GCC_WARN_ABOUT_RETURN_TYPE = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
+ HEADER_SEARCH_PATHS = "${SRCROOT}/external/gdata/Source/build/${CONFIGURATION}/GData.framework/Headers";
PREBINDING = NO;
SDKROOT = macosx10.5;
};
4 BirthdaySyncConstants.h
View
@@ -3,4 +3,6 @@ extern NSString *kUsernamePref;
extern NSString *kCalendarPref;
extern NSString *kEnableSyncPref;
-extern NSString *kSyncServicesClientId;
+extern NSString *kSyncServicesClientId;
+
+extern NSString *kBirthdaySyncUserAgent;
4 BirthdaySyncConstants.m
View
@@ -4,4 +4,6 @@
NSString *kCalendarPref = @"googleCalendar";
NSString *kEnableSyncPref = @"enableSync";
-NSString *kSyncServicesClientId = @"com.nparry.BirthSync";
+NSString *kSyncServicesClientId = @"com.nparry.BirthSync";
+
+NSString *kBirthdaySyncUserAgent = @"BirthdaySync-0.1";
9 BirthdaySyncer.h
View
@@ -1,10 +1,13 @@
#import <Cocoa/Cocoa.h>
#import <SyncServices/SyncServices.h>
+#import "GData/GData.h"
@interface BirthdaySyncer : NSObject <ISyncSessionDriverDataSource> {
- NSOperationQueue *queue;
- NSString *clientId;
- NSArray *entityNames;
+ NSOperationQueue *queue_;
+ NSString *clientId_;
+ NSArray *entityNames_;
+ GDataServiceGoogleCalendar *calendarService_;
+ GDataEntryCalendar *targetCalendar_;
}
+ (void) registerWithSyncServices;
139 BirthdaySyncer.m
View
@@ -1,14 +1,20 @@
#import "BirthdaySyncer.h"
#import "BirthdaySyncConstants.h"
+#import "PasswordStorage.h"
@interface BirthdaySyncer (Private)
-(void)runSync;
-(void)runSyncWithCallback:(id)data;
+-(void)setupCalendarData;
+-(NSString*)targetCalendarName;
+-(GDataEntryCalendar*)getTargetCalendar;
+-(GDataEntryCalendar*)createTargetCalendar;
+-(id)waitForTicket:(GDataServiceTicketBase*)ticket;
@end
@interface SyncerCallback : NSObject {
- id callbackObject;
- SEL callbackSelector;
+ id callbackObject_;
+ SEL callbackSelector_;
}
-(id)initWithObject:(id)ojbect selector:(SEL)selector;
-(void)invoke:(BirthdaySyncer*)bs;
@@ -17,14 +23,14 @@ -(void)invoke:(BirthdaySyncer*)bs;
@implementation SyncerCallback
-(id)initWithObject:(id)object selector:(SEL)selector {
if (self = [super init]) {
- callbackObject = object;
- callbackSelector = selector;
+ callbackObject_ = object;
+ callbackSelector_ = selector;
}
return self;
}
-(void)invoke:(BirthdaySyncer*)bs {
- [callbackObject performSelector:callbackSelector withObject:bs];
+ [callbackObject_ performSelector:callbackSelector_ withObject:bs];
}
@end
@@ -54,9 +60,19 @@ + (void) unregisterFromSyncServices {
-(id)init {
if (self = [super init]) {
- queue = [[NSOperationQueue alloc] init];
- clientId = 0;
- entityNames = 0;
+ queue_ = [[NSOperationQueue alloc] init];
+ clientId_ = NULL;
+ entityNames_ = NULL;
+
+ NSString *username = [[NSUserDefaults standardUserDefaults] stringForKey:@"googleUsername"];
+ NSString *password = getBirthdaySyncPassword();
+
+ calendarService_ = [[GDataServiceGoogleCalendar alloc] init];
+ [calendarService_ setUserAgent:kBirthdaySyncUserAgent];
+ [calendarService_ setShouldCacheDatedData:YES];
+ [calendarService_ setServiceShouldFollowNextLinks:YES];
+ [calendarService_ setUserCredentialsWithUsername:username
+ password:password];
}
return self;
}
@@ -64,20 +80,23 @@ -(id)init {
-(id)initWithClient:(NSString*)client
entityNames:(NSArray*)entities {
if (self = [super init]) {
- clientId = [client retain];
- entityNames = [entities retain];
+ clientId_ = [client retain];
+ entityNames_ = [entities retain];
}
return self;
}
-(void)dealloc {
- [queue release];
- [clientId release];
- [entityNames release];
+ [queue_ release];
+ [clientId_ release];
+ [entityNames_ release];
+ [calendarService_ release];
+ [targetCalendar_ release];
[super dealloc];
}
- (void) runSynchronousSync {
+ //[self setupCalendarData];
NSOperationQueue *q = [[NSOperationQueue alloc] init];
NSInvocationOperation* op = [[NSInvocationOperation alloc] initWithTarget:self
selector:@selector(runSync)
@@ -94,17 +113,18 @@ - (void) runSynchronousSync {
- (void) runAsynchronousSyncAndCall:(id)object
selector:(SEL)sel {
+ //[self setupCalendarData];
SyncerCallback *cb = [[SyncerCallback alloc] initWithObject:object selector:sel];
NSInvocationOperation* op = [[NSInvocationOperation alloc] initWithTarget:self
selector:@selector(runSyncWithCallback:)
object:cb];
- [queue addOperation:op];
+ [queue_ addOperation:op];
[op release];
[cb release];
}
- (NSString *)clientIdentifier {
- return clientId? clientId : kSyncServicesClientId;
+ return clientId_? clientId_ : kSyncServicesClientId;
}
- (NSURL *)clientDescriptionURL {
@@ -121,6 +141,13 @@ - (ISyncSessionDriverMode)preferredSyncModeForEntityName:(NSString *)entity {
}
- (NSDictionary *)recordsForEntityName:(NSString *)entity
+ moreComing:(BOOL *)moreComing
+ error:(NSError **)outError {
+ *moreComing = NO;
+ return [NSDictionary dictionary];
+}
+
+- (NSDictionary *)changedRecordsForEntityName:(NSString *)entity
moreComing:(BOOL *)moreComing
error:(NSError **)outError {
*moreComing = NO;
@@ -151,8 +178,86 @@ -(void)runSyncWithCallback:(id)object {
}
-(void)runSync {
- ISyncSessionDriver *syncDriver = [ISyncSessionDriver sessionDriverWithDataSource:self];
- BOOL success = [syncDriver sync];
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+
+ @try {
+ [self setupCalendarData];
+ ISyncSessionDriver *syncDriver = [ISyncSessionDriver sessionDriverWithDataSource:self];
+ [syncDriver sync];
+ } @catch (NSException *error) {
+ NSLog(@"Error during sync: %@", [error reason]);
+ }
+
+ [pool release];
+}
+
+-(void)setupCalendarData {
+ targetCalendar_ = [self getTargetCalendar];
+ if (!targetCalendar_) {
+ targetCalendar_ = [self createTargetCalendar];
+ }
+ [targetCalendar_ retain];
+}
+
+-(NSString*)targetCalendarName {
+ return [[NSUserDefaults standardUserDefaults] stringForKey:@"googleCalendar"];
+}
+
+-(GDataEntryCalendar*)getTargetCalendar {
+ NSString *targetName = [self targetCalendarName];
+
+ GDataServiceTicket *ticket =
+ [calendarService_ fetchCalendarFeedWithURL:[NSURL URLWithString:kGDataGoogleCalendarDefaultOwnCalendarsFeed]
+ delegate:self
+ didFinishSelector:NULL
+ didFailSelector:NULL];
+
+ GDataFeedCalendar *feed = [self waitForTicket:ticket];
+ NSEnumerator *enumerator = [[feed entries] objectEnumerator];
+ GDataEntryCalendar *calendar;
+ while (calendar = [enumerator nextObject]) {
+ if ([targetName isEqualToString:[[calendar title] stringValue]]) {
+ return calendar;
+ }
+ }
+
+ return NULL;
+}
+
+-(GDataEntryCalendar*)createTargetCalendar {
+ GDataEntryCalendar *newEntry = [GDataEntryCalendar calendarEntry];
+ [newEntry setTitleWithString:[self targetCalendarName]];
+ [newEntry setIsSelected:YES]; // check the calendar in the web display
+
+ // as of Dec. '07 the server requires a color,
+ // or returns a 404 (Not Found) error
+ [newEntry setColor:[GDataColorProperty valueWithString:@"#2952A3"]];
+
+ GDataServiceTicket *ticket =
+ [calendarService_ fetchCalendarEntryByInsertingEntry:newEntry
+ forFeedURL:[NSURL URLWithString:kGDataGoogleCalendarDefaultOwnCalendarsFeed]
+ delegate:self
+ didFinishSelector:NULL
+ didFailSelector:NULL];
+
+ GDataEntryCalendar *calendar = [self waitForTicket:ticket];
+ return calendar;
+}
+
+-(id)waitForTicket:(GDataServiceTicketBase*)ticket {
+ NSError *error = NULL;
+ id result = NULL;
+
+ BOOL success = [calendarService_ waitForTicket:ticket
+ timeout:60
+ fetchedObject:&result
+ error:&error];
+
+ if (success) {
+ return result;
+ }
+
+ @throw error;
}
@end
1  external/gdata
@@ -0,0 +1 @@
+Subproject commit 4f8292dac9e2dae55d888b7fde38588e66599b8c
Please sign in to comment.
Something went wrong with that request. Please try again.