Facebook SDK 3.1 - Error validating access token

26,702

Solution 1

The Facebook account on the device has become out-of-sync with the server as well as with the App's/SDK's cache. This can be solved by calling the ACAccountStore method renewCredentialsForAccount, which will update the OS's understanding of the token state.

In the next update of the SDK, the SDK will automatically call this API when it receives a response from the server indicating that a token has become invalid. For the 3.1.0 revision of the SDK, applications will need to explicitly call this API. Here is a code sample:

ACAccountStore *accountStore;
ACAccountType *accountTypeFB;
if ((accountStore = [[ACAccountStore alloc] init]) &&
    (accountTypeFB = [accountStore accountTypeWithAccountTypeIdentifier:ACAccountTypeIdentifierFacebook] ) ){

    NSArray *fbAccounts = [accountStore accountsWithAccountType:accountTypeFB];
    id account;
    if (fbAccounts && [fbAccounts count] > 0 &&
        (account = [fbAccounts objectAtIndex:0])){

        [accountStore renewCredentialsForAccount:account completion:^(ACAccountCredentialRenewResult renewResult, NSError *error) {
            //we don't actually need to inspect renewResult or error.
            if (error){

            }
        }];
    }
}

There are several options for where/when to call the API. The simplest place would be to opportunistically make the call on application launch, or on view load. One problem with this approach is that it will cause a network round-trip that is often unnecessary. Another option is to call it when a session change notification occurs, indicating that a session has closed. Also many applications fetch some basic information such as graph.facebook.com/me, at application launch time, and if so -- a call to this method in case of an error response may be a reasonable place to ask iOS to update its token status.

Hopefully this helps!

Solution 2

I'm just going to contribute another thing to check that caused me to waste 3 hours: Make sure your FB app settings do not have the 'Sandbox' option on if you're trying to login with a non-app-developer FB user... Maybe obvious, but could save others a few hours hopefully.

Solution 3

Try adding, if you haven't already, your iOS App Bundle ID in the settings panel of your Facebook APP as suggested here.

Hope this helps.

Solution 4

I'm fairly sure this is a Facebook iOS SDK bug (even on 3.1.1) and I filed this bug report.

While trying to reproduce this bug using their sample app Scrumptious, I found that it allows you to successfully re-authorize if you are using openActiveSessionWithReadPermissions. However, if you are asking for publish permissions via openActiveSessionWithPublishPermissions, it would be stuck in com.facebook.sdk.error 5.

Share:
26,702
tarmes
Author by

tarmes

I've been a software engineer since 1994, working in various fields from compiler design to embedded systems for ink jet printers. Since 2010 I've been specialising in developing full-stack web applications and software for iOS (iPhone, iPad, iPod) and Mac. My own iOS applications are commercialiapplisoftwaresed via my development company Arctic Whiteness. I'm also known for my plugins for Adobe Lightroom. I'm passionate about great software design. Applications should be easy to use, capable and beautiful. Internally software architecture should have clear separation and purpose and be easy to maintain, extend and test. On a personal level, just like everyone else I'm a complex combination of many different abilities and interests. I'm a Brit living in the South of France, a freelance software developer, a husband, a dad of two, a passionate sailor, a photographer, a go player, a climber and a cook. I enjoy technology, astronomy, puzzle solving, teaching, travel, the mountains, the sea, music, working for myself and lots of other things besides. I am available for hire - please contact me to discuss any development work.

Updated on July 21, 2020

Comments

  • tarmes
    tarmes almost 4 years

    I'm trying to transition my app to the new Facebook SDK 3.1 (with support for iOS6 authentication).

    I had it working just fine, so I then decided to remove the app from my list of authorized apps on the FB website in order to test that iOS would ask for permission again.

    Now my first call to [FBRequest requestForMe] causes this error:

    Response:

    {
      "error": {
        "message": "Error validating access token: Session does not match current stored session. This may be because the user changed the password since the time the session was created or Facebook has changed the session for security reasons.",
        "type":"OAuthException",
        "code":190,
        "error_subcode":460
      }
    }
    

    Some details:

    I'm trying to open the session as follows :

       [FBSession openActiveSessionWithReadPermissions:nil
                                           allowLoginUI:YES
                                      completionHandler:^(FBSession *session, FBSessionState state, NSError *error) {
    
                                               switch (state) {
                                                   case FBSessionStateOpen:
                                                       [self presentPostOptions];
                                                       break;
    
                                                   case FBSessionStateClosed:
                                                   case FBSessionStateClosedLoginFailed:
                                                       [FBSession.activeSession closeAndClearTokenInformation];
                                                       break;
    
                                                   default:
                                                       break;
                                               }
    

    I then get called back in state FBSessionStateOpen (at this point iOS hasn't presented a request dialog, is that to be expected)? Facebook logs this:

    2012-09-26 13:43:43.768 MyApp[2177:907] FBSDKLog: FBSession INVALID transition from FBSessionStateCreated to FBSessionStateClosed
    2012-09-26 13:43:43.769 MyApp[2177:907] FBSDKLog: FBSession transition from FBSessionStateCreated to FBSessionStateCreatedOpening 
    2012-09-26 13:43:43.837 MyApp[2177:907] FBSDKLog: FBSession transition from FBSessionStateCreatedOpening to FBSessionStateOpen 
    

    Once the session is open, in presentPostOptions I do this:

    - (void)presentPostOptions
    {    
        [[FBRequest requestForMe] startWithCompletionHandler:^(FBRequestConnection *connection, NSDictionary<FBGraphUser> *user, NSError *error) {
            if (!error) {
                self.usersName = user.name;
                self.usersID = user.id;
    
                [self getPages];
            }
            else
            {
                [self didFailWithError:error];
            }
        }];
    }
    

    Before the above completion block is called back, my main state handler block is called with an FBSessionStateClosed state. In the meantime, the Facebook SDK has logged the above error.

    I can't find any way to reset the system; nor do I really understand the cause.

    Can anyone please shed some light?

  • tarmes
    tarmes almost 12 years
    Hi. I've just double checked that that's all entered correctly - it is, so that's not the issue.
  • tarmes
    tarmes almost 12 years
    Hi Jason. Thanks, I'll try that on Monday. Do you know when the next release of the SDK will be?
  • Jason Clark
    Jason Clark almost 12 years
    We are working on a dot-release, with a limited number of bug fixes. It should not be too far out.
  • Cyupa
    Cyupa almost 12 years
    I had the same issue and did that check, right after it worked.
  • tarmes
    tarmes over 11 years
    Hi Jason. Having just updated the rest of my app for iOS 6 I now need to get the FB integration sorted out. I'd much rather use a bug free version of the SDK than add my own hacks :) Are you able to give some rough indication of the release date - are we talking days or weeks? Thanks.
  • tarmes
    tarmes over 11 years
    For info, I can confirm that this did fix the issue. Now I'm waiting for the SDK update so that this can be done in the right place.
  • Jason Clark
    Jason Clark over 11 years
    Here is the update (3.1.1) that fixes this directly in the SDK: github.com/downloads/facebook/facebook-ios-sdk/… Thanks!!
  • tarmes
    tarmes over 11 years
    That's great, thanks Jason. In the change log you note that "This does NOT address the 'code 2' errors from when ios6 users toggle the slider in their device Facebook settings though those cases do transition to 'ClosedLoginFailed' so it can be argued clients can code against it". What does this mean, and what should we be doing?
  • Jason Clark
    Jason Clark over 11 years
    Hi @tarmes, there is nothing you need to do special here. This comment is actually specifically targeted at the user-experience of the scrumptious sample -- and was meant to note that scrumptious is going to continue to blindly pop-up a message box for any FBErrorLoginFailedOrCancelled case. Sorry for the misleading comment.
  • tarmes
    tarmes over 11 years
    Hi Jason. I've installed the 3.1.1 and removed the temporary fix above. Unfortunately the new SDK doesn't fix the issue. I've tracked down the problem - can we discuss this somewhere?
  • Jason Clark
    Jason Clark over 11 years
    Hi @tarmes please email me or Facebook message me, and we can dig in a bit deeper on the problem. Thanks!
  • tarmes
    tarmes over 11 years
    OK, I've describe the problem and fix via FB message. Thx, Tim.
  • ill_always_be_a_warriors
    ill_always_be_a_warriors over 11 years
    @JasonClark, is there a method in the 3.1.1 SDK that does what your code chunk above does? I am using that code to fix an account-switching "code 2" error and was wondering whether I can call it somewhere or have to create my own function.
  • Min Kim
    Min Kim over 11 years
    I didn't read the documentation carefully. You have to call openActiveSessionWithRead first, then write. It looks like you can't start with openActiveSessionWithPublishPermissions..
  • jowie
    jowie over 11 years
    Unfortunately still a problem for me using 3.1.1. When I log the fbAccounts array, all I get is an empty field. Annoyingly, I also accidentally selected "Don't Allow" on one of the dialogs and now I don't see any alerts at all... It just fails silently :(
  • TomSwift
    TomSwift over 11 years
    @JasonClark - I'm using 3.1.1 and experiencing a variety of related issues with this. One specific case is if the user removes their FB account from iOS settings the app/SDK still believe they have a valid token. And the token MAY be valid, but it seems wrong to continue using it if the user removed their account from Settings. And what if they then add a different FB account in iOS Settings - the app has no way of knowing to pick that up and use it instead of the cached session it has.
  • dizy
    dizy over 11 years
    I'm also getting this error after removing the app from my facebook account. When trying to fix, the fbAccounts array has nothing in it. Ideas?
  • Martin Reichl
    Martin Reichl over 11 years
    Proof. This certainly helps!
  • minovsky
    minovsky over 11 years
    I just updated to SDK 3.2, still have this problem.... (tested on ios6.0 iphone5)
  • Kaigi
    Kaigi about 11 years
    Can anyone explain why "we don't actually need to inspect renewResult or error"?
  • jjxtra
    jjxtra almost 11 years
    Still have this problem on SDK 3.7.1