Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I get refresh token using GIDSignIn and GTMOAuth2Authentication in iOS?

I am writing an iOS app that uses Google's GIDSignIn [1] to sign in users and GTLServiceYoutube to execute queries against Youtube (uploading videos and retrieving Youtube video lists).

This works fine when the user first logs in but after approximately one hour, the access token expires and the user is no longer able to execute queries with GTLServiceYoutube due to a 401 error (invalid credentials).

I use the following code to set the GTMOAuth2Authentication after successful login:

- (void)signIn:(GIDSignIn *)signIn didSignInForUser:(GIDGoogleUser *)user withError:(NSError *)error {

    if (error == nil) {
        [self setAuthorizerForSignIn:signIn user:user];
    }
    [super signIn:signIn didSignInForUser:user withError:error];
}

- (void)setAuthorizerForSignIn:(GIDSignIn *)signIn user:(GIDGoogleUser *)user {
     GTMOAuth2Authentication *auth = [[GTMOAuth2Authentication alloc] init];

    [auth setClientID:signIn.clientID];
    [auth setClientSecret:[[NSBundle mainBundle] objectForInfoDictionaryKey:@"GoogleClientSecret"]];
    [auth setUserEmail:user.profile.email];
    [auth setUserID:user.userID];
    [auth setAccessToken:user.authentication.accessToken];
    [auth setRefreshToken:user.authentication.refreshToken];
    [auth setExpirationDate: user.authentication.accessTokenExpirationDate];
    [[UserManager sharedInstance].youTubeService setAuthorizer:auth];
}

where [[UserManager sharedInstance].youTubeService is an instance of GTLServiceYouTube.

The only problem is with the GTLServiceYouTube. GIDSignIn seems to handle the refresh tokens, so that the user is always logged in after the first login. But the GTLOAuth2Authentication only works on the first login and is broken after one hour.

So my question is: Am I doing something wrong here? Or am I missing something to get the proper access token in GTMOAuth2Authentication after refresh?

[1] https://developers.google.com/identity/sign-in/ios/api/interface_g_i_d_sign_in

like image 832
hjortgaard Avatar asked May 29 '15 06:05

hjortgaard


2 Answers

I believe the correct way to do this is by signing the user back in when the app is reopened or the token needs to be refreshed. This can be done by calling [[GIDSignIn sharedInstance] signInSilently] and then, when it finishes signing in update the keychain or datastore with your new auth tokens.

like image 198
charliebeckwith Avatar answered Sep 28 '22 23:09

charliebeckwith


As of GoogleSignIn 2.1.0, making a call to [GIDSignIn sharedInstance].signInSilently; updates the credentials stored in [GIDSignIn sharedInstance].currentUser.authentication.

Run pod update on your project to update to the 2.1.0 SDK if you're using Cocoapods.

like image 32
class Avatar answered Sep 28 '22 22:09

class



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!