Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Obtaining a basic google auth-token from AccountManager

I want to obtain a Google Authtoken from the AccountManager that I can send to my Webservice (not hosted on App Engine) to authenticate the User (I just need the email address and eventually his name, if no permission is required for this).

What do I have to use for the "authTokenType" Paramter of the "getAuthToken" method?

And which google Api do I have to use to get the Users Email?

like image 468
Andreas Ka Avatar asked May 12 '12 17:05

Andreas Ka


2 Answers

This is doable using OpenID Connect, however it's sort of experimental, so details could change in the future. If you get an OAuth token for the 'https://www.googleapis.com/auth/userinfo.email' or 'https://www.googleapis.com/auth/userinfo.profile' scope you can use it to get user info from https://www.googleapis.com/oauth2/v1/userinfo (including email). Of course the user needs to authorize this.

You should theoretically be able to get the token from AcccountManager using the "oauth2:https://www.googleapis.com/auth/userinfo.profile" as the token type, but that doesn't appear to work on my device (Galaxy Nexus with stock 4.0.4). Since getting a token via the AccountManager doesn't work (at least for now), the only reliable way is to use a WebView and get one via the browser as described here: https://developers.google.com/accounts/docs/MobileApps

There is a demo web app here that does this: https://oauthssodemo.appspot.com

(late) Update: Google Play Services has been released and it is the preferred way to get an OAuth token. It should be available on all devices with Android 2.2 and later. Getting a profile token does work with it, in fact they use it in the demo app

like image 149
Nikolay Elenkov Avatar answered Oct 21 '22 01:10

Nikolay Elenkov


I have had problems with this as well, since I was not able to find anything like a reference. Perhaps this can help you (code copied from an Android example on using the account manager):

  1. Somewhere in an event handler of your Android app, issue a request for an auth token to get the user's email address in Android:

    _accountMgr = AccountManager.get(this);
    Account [] accounts = _accountMgr.getAccounts();                
    Account account = accounts[0];   // For me this is Google, still need to figure out how to get it by name.
    _accountMgr.getAuthToken(account, AUTH_TOKEN_TYPE, false, new GetAuthTokenCallback(), null);
    
  2. In the callback, extract the access token:

    private class GetAuthTokenCallback implements AccountManagerCallback<Bundle> {
        public void run(AccountManagerFuture<Bundle> result) {
            Bundle bundle;
            try {
                bundle = result.getResult();
                final String access_token = bundle.getString(AccountManager.KEY_AUTHTOKEN);
                // store token somewhere you can supply it to your web server.
            } catch (Exception e) {
                // do something here.
            }
        }
    }
    
  3. Make some request to your web server, supplying the access token.

  4. On the web server, validate the access token and obtain the email address:

    curl -d 'access_token=<this is the token the app sent you>' https://www.googleapis.com/oauth2/v1/tokeninfo
    

    You should get something like this:

    {
      "issued_to": "<something>.apps.googleusercontent.com",
      "audience": "<something>.apps.googleusercontent.com",
      "scope": "https://www.googleapis.com/auth/userinfo.email",
      "expires_in": 3562,
      "email": "<users email address>",
      "verified_email": true,
      "access_type": "online"
    }
    

    or if something went wrong:

    {
      "error": "invalid_token",
      "error_description": "Bad Request"
    }
    
like image 23
Martijn de Milliano Avatar answered Oct 21 '22 00:10

Martijn de Milliano