I am developing an Android app. With the impending deprecation of Facebook's offline_access permission I am trying to use the Graph API to extend the Facebook token.
https://graph.facebook.com/oauth/access_token?
client_id=APP_ID&
client_secret=APP_SECRET&
grant_type=fb_exchange_token&
fb_exchange_token=EXISTING_ACCESS_TOKEN
Can anyone provide detailed code that demonstrates how to implement the code above into an android app and obtain the refreshed Facebook token?
Thank you for your time.
Update Two:
Progress (I think)!
Using the full URL with the facebook request method results in the base URL being added to the the beginning of the URL So instead of
String refreshUrl = "https://graph.facebook.com/oauth/access_token?client_id=12345678910&client_secret=abcdefghijklmnopqrstuvwxyz&grant_type=fb_exchange_token&fb_exchange_token="+currentAccessToken;
should use
String refreshUrl = "oauth/access_token?client_id=12345678910&client_secret=abcdefghijklmnopqrstuvwxyz&grant_type=fb_exchange_token&fb_exchange_token="+currentAccessToken;
However I am now getting the response {"error":{"message":"Error validating application. Invalid application ID.","type":"OAuthException","code":190}}
Update One:
Here is what I have I tried. The code completes, that is OnComplete on the listerner is called, BUT the response does not contain a new access token or expiry value.
void refreshWithGraph() {
AsyncFacebookRunner extendingAsyncRunner = new AsyncFacebookRunner(facebook);
Bundle parameters = new Bundle();
//the variable currentAccessToken is obtained after authorisation is complete using currentAccessToken = facebook.getAccessToken();
String refreshUrl = "https://graph.facebook.com/oauth/access_token?client_id=12345678910&client_secret=abcdefghijklmnopqrstuvwxyz&grant_type=fb_exchange_token&fb_exchange_token="+currentAccessToken;
extendingAsyncRunner.request(refreshUrl, parameters, new RefreshListener(), null );
}
Here is my version of RefreshListener...
//REFRESH LISTENER
public class RefreshListener extends BaseRequestListener {
public void onComplete(final String response, Object state) {
try {
final JSONObject json = Util.parseJson(response);
runOnUiThread(new Runnable() {
@Override
public void run() {
tvRefreshResponse.setText("IN REFRESH LISTENER ONCOMPLETE\nResponse is " + response);
tvRefreshToken.setText("IN REFRESH LISTENER ONCOMPLETE\nToken is " + facebook.getAccessToken());
tvRefreshExpiry.setText("IN REFRESH LISTENER ONCOMPLETE\nFacebook expiry is " + millisecToDate(facebook.getAccessExpires()));
}
}); //end runOnUiThread
} catch (JSONException e) {
runOnUiThread(new Runnable() {
@Override
public void run() {
tvRefreshResponse.setText("IN REFRESH LISTENER ONCOMPLETE CAUGHT JSON EXCEPTION \nResponse is " + response);
}
}); //end runOnUiThread
} catch (FacebookError fe) {
runOnUiThread(new Runnable() {
@Override
public void run() {
tvRefreshResponse.setText("IN REFRESH LISTENER ONCOMPLETE CAUGHT FACEBOOK ERROR \nResponse is " + response);
}
}); //end runOnUiThread
} //end catch Facebook error
} //end onComplete
@Override
public void onIOException(IOException e, Object state) {
tvRefreshResponse.setText("IN REFRESH LISTENER IOEXCEPTION \nException is "+ e.getLocalizedMessage());
}
@Override
public void onFileNotFoundException(FileNotFoundException e, Object state) {
tvRefreshResponse.setText("IN REFRESH LISTENER FILE NOT FOUND EXCEPTION \nException is "+ e.getLocalizedMessage());
}
@Override
public void onMalformedURLException(MalformedURLException e, Object state) {
tvRefreshResponse.setText("IN REFRESH MALFORMED URL \nException is "+ e.getLocalizedMessage());
}
@Override
public void onFacebookError(FacebookError e, Object state) {
tvRefreshResponse.setText("IN REFRESH ONFACEBOOK ERROR \nException is "+ e.getLocalizedMessage());
}
} //end RefreshListener
The code completes, that is OnComplete on the listerner is called, BUT the response does not contain a new access token or expiry value. The response is...
{"id":"https:\/\/graph.facebook.com\/oauth\/access_token","shares":78,"comments":1}
When I put the same URL (with a alphanumeric current token value) into a web browser the response DOES include an access token.
Related Info
Facebook's offline_access permission will be deprecated on 1st of May, 2012
Please don't suggest using the extendAccessTokenIfNeeded function in onResume() instead. I am also having trouble with that and it is the reason why I am looking into the Graph API token refreshing :-)
Related Stack Overflow Questions
Is it possible to extend Facebook tokens with extendAccessTokenIfNeeded in an Android app? (my question)
How would offline_access work after deprecation after May 1st?
Facebook access token can not be extended
Protecting app secret for extendAccessToken usage (Java/Android)
Relevant Facebook links
Facebook Android Tutorial
Facebook offline_access permission deprecation