Skip to content
Snippets Groups Projects
Commit 186d6d40 authored by cramakri's avatar cramakri
Browse files

Added support for a Dead openBIS connection that does not actually retrieve data

SVN: 27645
parent 5cc544e4
No related branches found
No related tags found
No related merge requests found
...@@ -24,6 +24,13 @@ ...@@ -24,6 +24,13 @@
#import <Foundation/Foundation.h> #import <Foundation/Foundation.h>
#import "CISDOBShared.h" #import "CISDOBShared.h"
//! The error domain for errors in the Connection layer
FOUNDATION_EXPORT NSString *const CISDOBConnectionErrorDomain;
enum CISDOBConnectionErrorCode {
kCISDOBConnectionError_NoServerAvailable = 1,
};
/** /**
* \brief A connection to an openBIS server. * \brief A connection to an openBIS server.
...@@ -83,3 +90,14 @@ ...@@ -83,3 +90,14 @@
} }
@end @end
/**
* \brief A fake connection to openBIS
*
*/
@interface CISDOBDeadConnection : CISDOBConnection {
@private
}
@end
...@@ -25,6 +25,8 @@ ...@@ -25,6 +25,8 @@
#import "CISDOBJsonRpcCall.h" #import "CISDOBJsonRpcCall.h"
#import "CISDOBAsyncCall.h" #import "CISDOBAsyncCall.h"
NSString *const CISDOBConnectionErrorDomain = @"CISDOBConnectionErrorDomain";
// Internal connection call that includes the private state // Internal connection call that includes the private state
@interface CISDOBConnectionCall : CISDOBAsyncCall { @interface CISDOBConnectionCall : CISDOBAsyncCall {
@private @private
...@@ -158,6 +160,22 @@ ...@@ -158,6 +160,22 @@
@end @end
@implementation CISDOBDeadConnection
- (void)executeCall:(CISDOBConnectionCall *)call
{
void (^notifyBlock)(void) = ^ {
NSString *errorMessage = @"The app is not connected to an openBIS server.";
NSDictionary *userInfo =
[NSDictionary dictionaryWithObjectsAndKeys: errorMessage, NSLocalizedDescriptionKey, nil];
NSError *error = [NSError errorWithDomain: CISDOBConnectionErrorDomain code: kCISDOBConnectionError_NoServerAvailable userInfo: userInfo];
call.failWrapper(error);
};
[[NSOperationQueue mainQueue] addOperationWithBlock: notifyBlock];
}
@end
@implementation CISDOBConnectionCall @implementation CISDOBConnectionCall
......
...@@ -25,7 +25,11 @@ ...@@ -25,7 +25,11 @@
#import "CISDOBShared.h" #import "CISDOBShared.h"
// //
// The names of the notifications posted by the service manager // The names of the notifications posted by the service manager.
//
// The notifications include a userInfo dictionary with the following
// keys and values:
// NSUnderlyingErrorKey If in the dictionary, the error that occured when making the call.
// //
FOUNDATION_EXPORT NSString *const CISDOBIpadServiceWillLoginNotification; FOUNDATION_EXPORT NSString *const CISDOBIpadServiceWillLoginNotification;
FOUNDATION_EXPORT NSString *const CISDOBIpadServiceDidLoginNotification; FOUNDATION_EXPORT NSString *const CISDOBIpadServiceDidLoginNotification;
...@@ -44,12 +48,14 @@ FOUNDATION_EXPORT NSString *const CISDOBIpadServiceDidSynchEntitiesNotification; ...@@ -44,12 +48,14 @@ FOUNDATION_EXPORT NSString *const CISDOBIpadServiceDidSynchEntitiesNotification;
@class CISDOBIpadService, CISDOBAsyncCall, CISDOBIpadEntity; @class CISDOBIpadService, CISDOBAsyncCall, CISDOBIpadEntity;
/** /**
* \brief A class that manages a connection to the openBIS iPad service, caching data locally as CISDOBIpadEntity objects. * \brief A class that manages a connection to the openBIS iPad service, caching data locally as CISDOBIpadEntity objects.
*/ */
@interface CISDOBIpadServiceManager : NSObject @interface CISDOBIpadServiceManager : NSObject
@property (readonly) NSURL *openbisUrl;
@property (readonly, strong) CISDOBIpadService *service; @property (readonly, strong) CISDOBIpadService *service;
@property (readonly, strong) NSURL *storeUrl; @property (readonly, strong) NSURL *storeUrl;
@property (readonly, strong) NSManagedObjectContext *managedObjectContext; @property (readonly, strong) NSManagedObjectContext *managedObjectContext;
...@@ -63,6 +69,9 @@ FOUNDATION_EXPORT NSString *const CISDOBIpadServiceDidSynchEntitiesNotification; ...@@ -63,6 +69,9 @@ FOUNDATION_EXPORT NSString *const CISDOBIpadServiceDidSynchEntitiesNotification;
// Initialization // Initialization
- (id)initWithStoreUrl:(NSURL *)storeUrl openbisUrl:(NSURL *)openbisUrl trusted:(BOOL)trusted error:(NSError **)error; - (id)initWithStoreUrl:(NSURL *)storeUrl openbisUrl:(NSURL *)openbisUrl trusted:(BOOL)trusted error:(NSError **)error;
// Properties
- (void)setOpenbisUrl:(NSURL *)openbisUrl trusted:(BOOL)trusted;
// Actions // Actions
//! Log the user into the openBIS instance //! Log the user into the openBIS instance
......
...@@ -42,12 +42,11 @@ NSString *const CISDOBIpadServiceDidSynchEntitiesNotification = @"CISDOBIpadServ ...@@ -42,12 +42,11 @@ NSString *const CISDOBIpadServiceDidSynchEntitiesNotification = @"CISDOBIpadServ
// Internal service call that includes the private state // Internal service call that includes the private state
@interface CISDOBIpadServiceManagerCall : CISDOBAsyncCall @interface CISDOBIpadServiceManagerCall : CISDOBAsyncCall
@property(weak) CISDOBIpadServiceManager *serviceManager; @property(weak, nonatomic) CISDOBIpadServiceManager *serviceManager;
@property(nonatomic) CISDOBAsyncCall *serviceCall; @property(nonatomic) CISDOBAsyncCall *serviceCall;
@property(copy) NSString *willCallNotificationName;
@property(copy) NSString *didCallNotificationName;
@property(nonatomic) BOOL sendSynchNotifications; @property(copy, nonatomic) NSString *willCallNotificationName; //<! The notification called before the call takes place, may be nil
@property(copy, nonatomic) NSString *didCallNotificationName; //<! The notification called after the call has completed, may be nil
// Initialization // Initialization
- (id)initWithServiceManager:(CISDOBIpadServiceManager *)serviceManager serviceCall:(CISDOBAsyncCall *)call; - (id)initWithServiceManager:(CISDOBIpadServiceManager *)serviceManager serviceCall:(CISDOBAsyncCall *)call;
...@@ -73,7 +72,7 @@ NSString *const CISDOBIpadServiceDidSynchEntitiesNotification = @"CISDOBIpadServ ...@@ -73,7 +72,7 @@ NSString *const CISDOBIpadServiceDidSynchEntitiesNotification = @"CISDOBIpadServ
// Actions // Actions
- (void)run; - (void)run;
- (void)notifyCallOfResult:(id)args; - (void)notifyCallOfResult;
@end @end
...@@ -108,7 +107,13 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -108,7 +107,13 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
{ {
if (!(self = [super init])) return nil; if (!(self = [super init])) return nil;
CISDOBLiveConnection *connection = [[CISDOBLiveConnection alloc] initWithUrl: openbisUrl trusted: trusted]; CISDOBConnection *connection;
if (openbisUrl) {
connection = [[CISDOBLiveConnection alloc] initWithUrl: openbisUrl trusted: trusted];
} else {
connection = [[CISDOBDeadConnection alloc] init];
}
_storeUrl = [storeUrl copy]; _storeUrl = [storeUrl copy];
_service = [[CISDOBIpadService alloc] initWithConnection: connection]; _service = [[CISDOBIpadService alloc] initWithConnection: connection];
_managedObjectContext = GetMainThreadManagedObjectContext(self.storeUrl, error); _managedObjectContext = GetMainThreadManagedObjectContext(self.storeUrl, error);
...@@ -123,6 +128,28 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -123,6 +128,28 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
return self; return self;
} }
- (NSURL *)openbisUrl
{
if (![_service.connection isKindOfClass: [CISDOBLiveConnection class]]) return nil;
return ((CISDOBLiveConnection *) _service.connection).url;
}
- (void)setOpenbisUrl:(NSURL *)openbisUrl trusted:(BOOL)trusted;
{
if ([self.openbisUrl isEqual: openbisUrl]) return;
CISDOBConnection *connection;
if (openbisUrl) {
connection = [[CISDOBLiveConnection alloc] initWithUrl: openbisUrl trusted: trusted];
} else {
connection = [[CISDOBDeadConnection alloc] init];
}
_service = [[CISDOBIpadService alloc] initWithConnection: connection];
}
- (NSString *)sessionToken - (NSString *)sessionToken
{ {
return ((CISDOBLiveConnection *)(self.service.connection)).sessionToken; return ((CISDOBLiveConnection *)(self.service.connection)).sessionToken;
...@@ -131,10 +158,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -131,10 +158,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
- (void)syncEntities:(NSArray *)rawEntities pruning:(BOOL)prune notifying:(CISDOBIpadServiceManagerCall *)managerCall - (void)syncEntities:(NSArray *)rawEntities pruning:(BOOL)prune notifying:(CISDOBIpadServiceManagerCall *)managerCall
{ {
void (^syncBlock)(void) = ^{ void (^syncBlock)(void) = ^{
if (managerCall.didCallNotificationName) {
[[NSNotificationCenter defaultCenter] postNotificationName: managerCall.didCallNotificationName object: self];
}
[[NSNotificationCenter defaultCenter] postNotificationName: CISDOBIpadServiceWillSynchEntitiesNotification object: self]; [[NSNotificationCenter defaultCenter] postNotificationName: CISDOBIpadServiceWillSynchEntitiesNotification object: self];
// Run the synchronizer in the background thread // Run the synchronizer in the background thread
...@@ -153,7 +176,7 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -153,7 +176,7 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
notifySynchronizer.error = error; notifySynchronizer.error = error;
} }
} }
[notifySynchronizer notifyCallOfResult: nil]; [notifySynchronizer notifyCallOfResult];
}; };
[[NSOperationQueue mainQueue] addOperationWithBlock: notifyBlock]; [[NSOperationQueue mainQueue] addOperationWithBlock: notifyBlock];
}; };
...@@ -165,11 +188,11 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -165,11 +188,11 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
CISDOBIpadServiceManagerCall *managerCall = [[CISDOBIpadServiceManagerCall alloc] initWithServiceManager: self serviceCall: serviceCall]; CISDOBIpadServiceManagerCall *managerCall = [[CISDOBIpadServiceManagerCall alloc] initWithServiceManager: self serviceCall: serviceCall];
serviceCall.success = ^(id result) { serviceCall.success = ^(id result) {
// Update the cache // Update the cache and call the managerCall success when done
[self syncEntities: result pruning: prune notifying: managerCall]; [self syncEntities: result pruning: prune notifying: managerCall];
}; };
serviceCall.fail = ^(NSError *error) { if (managerCall.fail) managerCall.fail(error); }; serviceCall.fail = ^(NSError *error) { [managerCall notifyFailure: error]; };
return managerCall; return managerCall;
} }
...@@ -186,7 +209,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -186,7 +209,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
call.success = ^(id result) { [managerCall notifySuccess: result]; }; call.success = ^(id result) { [managerCall notifySuccess: result]; };
managerCall.willCallNotificationName = CISDOBIpadServiceWillLoginNotification; managerCall.willCallNotificationName = CISDOBIpadServiceWillLoginNotification;
managerCall.didCallNotificationName = CISDOBIpadServiceDidLoginNotification; managerCall.didCallNotificationName = CISDOBIpadServiceDidLoginNotification;
managerCall.sendSynchNotifications = NO;
return managerCall; return managerCall;
} }
...@@ -198,7 +220,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -198,7 +220,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
managerCall.willCallNotificationName = CISDOBIpadServiceWillRetrieveRootLevelEntitiesNotification; managerCall.willCallNotificationName = CISDOBIpadServiceWillRetrieveRootLevelEntitiesNotification;
managerCall.didCallNotificationName = CISDOBIpadServiceDidRetrieveRootLevelEntitiesNotification; managerCall.didCallNotificationName = CISDOBIpadServiceDidRetrieveRootLevelEntitiesNotification;
managerCall.sendSynchNotifications = YES;
return managerCall; return managerCall;
} }
...@@ -210,7 +231,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -210,7 +231,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
managerCall.willCallNotificationName = CISDOBIpadServiceWillDrillOnEntityNotification; managerCall.willCallNotificationName = CISDOBIpadServiceWillDrillOnEntityNotification;
managerCall.didCallNotificationName = CISDOBIpadServiceDidDrillOnEntityNotification; managerCall.didCallNotificationName = CISDOBIpadServiceDidDrillOnEntityNotification;
managerCall.sendSynchNotifications = YES;
return managerCall; return managerCall;
} }
...@@ -222,7 +242,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -222,7 +242,6 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
managerCall.willCallNotificationName = CISDOBIpadServiceWillRetrieveDetailsForEntityNotification; managerCall.willCallNotificationName = CISDOBIpadServiceWillRetrieveDetailsForEntityNotification;
managerCall.didCallNotificationName = CISDOBIpadServiceDidRetrieveDetailsForEntityNotification; managerCall.didCallNotificationName = CISDOBIpadServiceDidRetrieveDetailsForEntityNotification;
managerCall.sendSynchNotifications = YES;
return managerCall; return managerCall;
} }
...@@ -285,25 +304,25 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -285,25 +304,25 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
return self; return self;
} }
- (void)sendCompletionNotification - (void)sendCompletionNotification:(NSError *)errorOrNil
{ {
if (self.sendSynchNotifications) { if (self.didCallNotificationName) {
// This is handled elsewhere NSMutableDictionary *userInfo = [NSMutableDictionary dictionary];
} else if (self.didCallNotificationName) { if (errorOrNil) [userInfo setValue: errorOrNil forKey: NSUnderlyingErrorKey];
[[NSNotificationCenter defaultCenter] postNotificationName: self.didCallNotificationName object: self.serviceManager]; [[NSNotificationCenter defaultCenter] postNotificationName: self.didCallNotificationName object: self.serviceManager userInfo: userInfo];
} }
} }
- (void)notifySuccess:(id)result - (void)notifySuccess:(id)result
{ {
[self sendCompletionNotification: nil];
if (self.success) self.success(result); if (self.success) self.success(result);
[self sendCompletionNotification];
} }
- (void)notifyFailure:(NSError *)error - (void)notifyFailure:(NSError *)error
{ {
[self sendCompletionNotification: error];
if (self.fail) self.fail(error); if (self.fail) self.fail(error);
[self sendCompletionNotification];
} }
- (void)start - (void)start
...@@ -388,7 +407,7 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl ...@@ -388,7 +407,7 @@ static NSManagedObjectContext* GetMainThreadManagedObjectContext(NSURL* storeUrl
self.error = nil; self.error = nil;
} }
- (void)notifyCallOfResult:(id)args - (void)notifyCallOfResult
{ {
if (self.error) { if (self.error) {
[self.managerCall notifyFailure: self.error]; [self.managerCall notifyFailure: self.error];
......
...@@ -248,4 +248,26 @@ ...@@ -248,4 +248,26 @@
[self checkFindingChildren]; [self checkFindingChildren];
} }
- (void)testNilUrl
{
[self.serviceManager setOpenbisUrl: nil trusted: YES];
CISDOBAsyncCall *call;
[self assertNotLoggedIn];
call = [self.serviceManager loginUser: GetDefaultUserName() password: GetDefaultUserPassword()];
[self configureAndRunCallSynchronously: call];
[self assertLoggedIn];
[self assertBeforeRootLevelCall];
call = [self.serviceManager retrieveRootLevelEntities];
[self configureAndRunCallSynchronously: call];
STAssertTrue(self.willRetrieveRootLevel, @"Should have retrieved root level");
STAssertTrue(self.didRetrieveRootLevel, @"Should have retrieved root level");
// No synch should have happened
STAssertNotNil(_callError, @"The service manager should have failed to return entities.");
}
@end @end
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment