How to Extend Access Token Validity Since Offline_Access Deprecation

How to extend access token validity since offline_access deprecation

Edit (August 14th 2012):

A week ago the official Facebook PHP SDK was updated. The function name was changed to setExtendedAccessToken, and it was decided we actually needed to destroy the session afterwards, to remove the risk of having two active sessions.

Also, the function no longer actually returns the token, but instead stores it within the persistant data. You can therefore get the new access token with the public function getAccessToken afterwards. Grab the new SDK from official Facebook PHP SDK github page to make sure you're up to date.

Original Answer:

I have added a new public function to the base_facebook.php file, which returns an new access token which expires in 60 days. You can make a request to this function after you've received the normal access token. I've not tested, but I assume you also need to enable 'deprecate offline_access" in your Advanced settings of the Developer App.

Just add this to your base_facebook.php inside the facebook class and make a call to it. It works for me.

 public function getExtendedAccessToken(){

try {
// need to circumvent json_decode by calling _oauthRequest
// directly, since response isn't JSON format.
$access_token_response =
$this->_oauthRequest(
$this->getUrl('graph', '/oauth/access_token'), array(
'client_id' => $this->getAppId(),
'client_secret' => $this->getAppSecret(),
'grant_type'=>'fb_exchange_token',
'fb_exchange_token'=>$this->getAccessToken()
)
);
} catch (FacebookApiException $e) {
// most likely that user very recently revoked authorization.
// In any event, we don't have an access token, so say so.
return false;
}

if (empty($access_token_response)) {
return false;
}

$response_params = array();
parse_str($access_token_response, $response_params);
if (!isset($response_params['access_token'])) {
return false;
}

return $response_params['access_token'];
}

Re offline_access deprecation: When to do the fb_exchange_token thing?

a) Yes, that approach works well. I do that with some of my apps.

b) Please see the 3rd item in this FAQ.
http://dominicminicoopers.blogspot.com/2012/03/facebook-access-tokens-and-offline.html

Can I exchange my 60 day access token for a new 60 day access token?

No, sorry you cannot. You can only exchange a valid (meaning current)
user access token for an extended one. You cannot extend an already
extended access token.

How to handle Facebook's deprecation of offline_access when you use token both in both iOS app and a server

Overview

I believe that the root of what facebook is trying to achieve is to prevent an app from having perpetual ever-lasting access to a user's account. So, with the new migration an app can only access an account for 60 days unless the user signs in again.

I don't work for facebook, but here are my findings from playing around with the facebook graph api.

General Solution

  1. Whenever a user signs in, take their access token and immediately extend/refresh it, and save it
  2. Record the expiration date of the access token
  3. When an access token expires (either from the recorded date, or a graph API exception telling you so), then notify the user that you don't have access, and ask them to sign in again.

Answers

A. When you authenticate through the newest Facebook iOS SDK, what is the default lifetime of the access token you get? This document says an extended token request will give you one that lasts 60 days. This other document talks about the first access token request and mentions varying validities but it's unclear and does it talk about specific validity times:

Here's how it works:

  1. The first sign-in grants you approximately two hours
  2. By refreshing the access token, you can get up to 60 days
  3. If the user doesn't sign in to those 60 days, there is no way to get access for longer without having them sign in.
  4. If the user de-authorizes your app, that 60 day windows ends immediately, and you will no longer have access.

B. For the client, now that the access token isn't necessarily long lived, is the right approach for us to: Let use login through FB, then detect whenever the access token is expired. If it is, then call into FB iOS SDK to re-authentication/re-authorize? (this should just trigger user to bounce out to FB iOS app, and in most cases come immediately back to our app with a new access token).

If the users access token is expired, your only option is to have them go through a login loop like you are talking about.

C. According to this blog post I found, you can only extend an access token once. On the client, I can just handle this by prompting a re-authentication/re-authorization as I mentioned in Question B. However, this doesn't work on our server. We could certainly have the server renew it once to 60 days, but what happens on the 61st day? The server just stops being able to sync the friend's list?

You can only extend an access token once. On the 61st day, you are out of luck. Best notify the user and let them know that unless they sign in, you won't be able to do anything.

D. It seems to make sense to check the validity of the FB access token every time the app starts or re-hydrates from sleep. What is the best way for our iOS app to check this? Is there a recommended endpoint to call to validate a token? Should we just call into https://graph.facebook.com/me passing the access token and checking the response?

I haven't be able to find an API equivalent of the Debug Console. This FB blog article talks about invalidated access tokens, but doesn't mention any API methods in particular meant to test the API.

I your suggestion of hitting https://graph.facebook.com/me would work just fine is exactly what they recommend in their example. In fact, I might use this approach in my app as a pro-active way of checking an access token.

Tid Bits

  • When you "refresh" an access token, a new access token will be returned. The response looks like: access_token=TOKEN&expires=5183912
  • You can only "refresh" an access token once. If you try to "refresh" the long-lived token returned from a previous call, it will return the same token, but doesn't throw an exception unless the token has expired. (in other words, you can safely try to refresh your token)
  • The default access token length seems to be around 2 hours
  • If you "refresh" an access token, that new access tokens seems to be the one that you'll get from the facebook API afterwards (instead of returning the original, short-lived access token)

Also, if you want to play around, these tools make it easy to test out your use case in a browser before burying it in your code:

  • Graph API Explorer - For creating and getting access tokens
  • Debug Console - For checking the expiry date of tokens before/after refresh
  • Refresh Endpoint - For manually testing extending your tokens

Extending Long-lived access tokens

Actually I cannot use the solution in How to handle expired tokens because my access_token is not yet expired. As I said, I'll be doing this in 55-59th day, before long-lived token expires.

It seems the user has granted a previous offline_access to the application. That's why both client-side and server-side auth flows return the long-lived access token. This happens even if migration is enabled in the app settings. Facebook should also note about this in their documentation. The solution is for the user to revoke the offline_access permission.

Hopefully all offline_access permissions will be revoked once they force the migration scheduled in May 2, see developer roadmap.

Case Closed. May this post help other users who encounter such rare situations.

Facebook 60 day access token and Deprecated Offline_Access

The point of migration settings for Facebook apps is to enable developers to test new features (or deprecation of old features) ahead of time in their apps and spot bugs that may arise. AS indicated on the Developer Roadmap, offline_access permission will be removed on May 1st and at that point, every app will act as if the migration setting you are testing is enabled.

You can find more information about this change here:
https://developers.facebook.com/docs/offline-access-deprecation/

The reason we do not automatically enable this without notice is because it would cause a lot of apps to break. Facebook have a breaking change policy which tries to avoid making those sorts of changes without a 90 day warning (and in this case, a migration setting).

Edit: offline access permission removal was pushed back to Oct 3rd.

Access Token expire time with offline_access permission

Access tokens returned when using the offline_access permission never expire.

Edit: According to the documentation the tokens are 'long-lived'. I'm assuming you will just have to handle the scenario where they no longer work (if that even happens).



Related Topics



Leave a reply



Submit