2014-04-15 11 views
5

Versione corta:Come utilizzare un token di accesso offline di Google per autenticarsi in background su iOS?

voglio usare il Google OAuth2 client for Objective C per creare un GTMOAuth2Authentication oggetto valido per me di utilizzare nella mia app, con un token di accesso offline ricevo dal mio backend. Come posso farlo?

La mia situazione:

La mia applicazione utilizza Analytics sola lettura scopo di ottenere alcuni dati su sito web (s) dell'utente. Il modo in cui lo realizzo è quello di accedere al ViewController GTMOAuth2ViewControllerTouch, fornito dal client Google OAuth2 per Objective C. Quindi mi fornisce l'oggetto valido GTMOAuth2Authentication, che posso utilizzare per interrogare Google Analytics tramite lo Google API client.

Ora, non vogliamo consentire agli utenti l'accesso a Google Analytics (alcuni non hanno account Google e in generale, vogliamo mantenere le informazioni semplici tramite l'app). Ciò significa che dobbiamo accedere con il nostro account (che ha accesso a tutti i dati di Analytics dei siti Web). Ovviamente non possiamo dare ai nostri utenti le nostre credenziali, quindi abbiamo dovuto trovare una soluzione per questo.

Il mio piano:

Penso che questo problema potrebbe essere risolto richiedendo il nostro (accesso offline) stringa di token dal nostro back-end (tramite crittografia SSL), salvandolo al portachiavi dell'utente e usarlo ulteriormente nel applicazione per interrogare Analytics. Quindi, permettiamo all'utente di accedere al nostro servizio (in modo che possiamo determinare a quali siti l'utente ha accesso) e mostrare i dati.

Il mio problema:

Ho cercato ovunque, guardato attraverso la documentazione (molto sottile) da parte di Google, ispezionato il codice sorgente di GTMOAuth2Authentication, ma io non riesco a avvolgere la mia testa intorno al problema. Mi sembra che ci sarebbe una soluzione come questa (perché io uso un approccio simile nel nostro CMS per permettere a un utente di postare sulla nostra bacheca di Facebook), quindi cosa mi manca qui?

Il codice di accesso corrente:

GTMOAuth2ViewControllerTouch *viewController = [[GTMOAuth2ViewControllerTouch alloc] 
                initWithScope:scope 
                clientID:kMyClientID 
                clientSecret:kMyClientSecret 
                keychainItemName:kKeychainItemName 
                completionHandler: 
    ^(GTMOAuth2ViewControllerTouch *viewController, GTMOAuth2Authentication *auth, NSError *error) { 
     if (error != nil) { 
      // Authentication failed 
      DebugLog(@"Failed!"); 
     } else { 
      // Authentication succeeded 
      DebugLog(@"Success!"); 

      // Update interface 
      self.loginButton.hidden = YES; 

      self.authentication = auth; 
     } 
    }]; 

Quello che ho cercato:

Ho provato a generare manualmente un oggetto GTMOAuth2Authentication e impostare tutti i parametri di me (portata, clientid, secretid, accedere a token, aggiornare il token, callbackuri, URL del token, ecc.), ma mi viene restituito un errore 401: Login richiesto quando provo a utilizzare l'oggetto per le query. Quindi immagino che non sia il modo di farlo.

vicini:

Grazie per la lettura!

+0

prova e acquisisci il progetto di esempio per Google Drive. Ha il codice Oauth in esso. Una volta compreso come funziona, dovresti essere in grado di modificarlo per la quale sempre API stai cercando. http://code.google.com/p/google-api-objectivec-client/source/browse/#svn%2Ftrunk%2FExamples%2FDriveSample – DaImTo

+0

Grazie per il suggerimento! Lo verificherò – Thermometer

+0

Non ho guardato Objective-c in 100 anni. Ma potrei essere in grado di aiutarti se rimani bloccato solo qui. Posso ancora leggerlo almeno posso darti suggerimenti su cosa fare. – DaImTo

risposta

5

Non è necessaria un'istanza GTMOAuth2Authentication. Quello che ti serve è creare la tua classe che implementa il protocollo GTMFetcherAuthorizationProtocol e assegnarlo come tuo autore.

MyAuth *myAuth = [[MyAuth alloc] initWithAccessToken:accessToken]; 
googleService.authorizer = myAuth; 

Questa classe deve autorizzare la richiesta in base al token di accesso che già possiedi. Il codice di questa classe dovrebbe essere simile a questo.

@interface MyAuth : NSObject<GTMFetcherAuthorizationProtocol>  
    @property (copy, nonatomic) NSString *accessToken; 
    @property (copy, readonly) NSString *userEmail; 
@end 

@implementation MyAuth 

- (void)authorizeRequest:(NSMutableURLRequest *)request 
       delegate:(id)delegate 
     didFinishSelector:(SEL)sel { 
    if (request) { 
     NSString *value = [NSString stringWithFormat:@"%s %@", GTM_OAUTH2_BEARER, self.accessToken]; 
     [request setValue:value forHTTPHeaderField:@"Authorization"]; 
    } 

    NSMethodSignature *sig = [delegate methodSignatureForSelector:sel]; 
    NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:sig]; 
    [invocation setSelector:sel]; 
    [invocation setTarget:delegate]; 
    [invocation setArgument:(__bridge void *)(self) atIndex:2]; 
    [invocation setArgument:&request atIndex:3]; 
    [invocation invoke]; 
} 

- (void)authorizeRequest:(NSMutableURLRequest *)request 
     completionHandler:(void (^)(NSError *error))handler { 
    if (request) { 
     NSString *value = [NSString stringWithFormat:@"%@ %@", @"Bearer", self.accessToken]; 
     [request setValue:value forHTTPHeaderField:@"Authorization"]; 
    } 
} 

- (BOOL)isAuthorizedRequest:(NSURLRequest *)request { 
    return NO; 
} 

- (void)stopAuthorization { 
} 

- (void)stopAuthorizationForRequest:(NSURLRequest *)request { 
} 

- (BOOL)isAuthorizingRequest:(NSURLRequest *)request { 
    return YES; 
} 

Spero che sia d'aiuto.

+0

come implementeresti questo in Swift 2.0? Come gestiresti l'NSInvocation dato che Swift non lo espone più? – sun

+0

hi @balkoth, ho requisiti simili. Ho creato il mio autore che implementa GTMFetcherAuthorizationProtocol come menzionato. Ottengo accesstoken dal server che ho impostato durante l'installazione dell'ist. Ho l'ID del messaggio di Gmail e voglio recuperare la posta completa da esso, Come devo procedere qui, Anche dove impostare clientID. –

Problemi correlati