facebook.login always navigate to facebook app even though user already logged in

Hi, piling on here - I seem to get the same problem:

Every relaunch of the app, on running facebook.login for a previosuly logged in user it quickly switches to Facebook to relogin with v4. With the old version, this login check could be done without app switching, which was just smoother - the facebook.login just ran in the backgorund of my code and smoothly updated. The jump between apps is quite jarring.

I figure the only way to get around this would be to locally save the access taken in a database, which to me doesn’t seem perfectly secure, and either way - if we want to use it to interact with Facebook, we need to do the “app switch login dance” again anyway?

I think this is quite an annoying issue, just wanted to bump and see if anyone has figured out any solution for this or has any suggestions?

To add more insult to injury: if we do this without an internet connection, the app just switches to facebook and lags out, instead of going back to my app. So if a user starts the app on an airplane for example they get booted out from the app pretty much. Before, since this was handled in the app, we could have much more graceful failing.

Is this really the expected behaviour?

You should be able to check to see if you have a token after calling .init() and not have to call .login() which causes the fast switch. See:

https://docs.coronalabs.com/plugin/facebook-v4/getCurrentAccessToken.html

There is code at the bottom to demonstrate this.

Rob

Thanks for your answer!

However, I’m not sure if I follow - there is no .init() function for Facebook (I’ve double checked by printing the entire “facebook” array, and I see no such function?

So calling it just gives me a runtime error.

And calling facebook.getCurrentAccessToken() just gives me a “nil”; in other words, I don’t have the token

Just to make sure we are talking about the same thing, I don’t mean resuming an app from having it suspended - but from force closing it. To re-state the problem more clearly:

 

  1. A user starts the app, and logs in to Facebook.

 

1.1. Upon this, I save a boolean in a local database like UserIsLoggedIn = true - to save the fact that the user was logged in. If we don’t, the user would have to manually relogin every time the app was force closed.

 

  1. User force quits the app (or updates it, or does any action that does a complete exit and relaunch of the app)

 

  1. User relaunches the app

 

  1. The app checks the database and if UserIsLoggedIn was true, then we quickly run facebook.login to relogin.

 

4.1a. Before, the facebook.login ran inside the app, so I just showed a quick “loading” indicator for a second, and the user was logged back in. Perfect!

 

4.1b. Now, facebook.login instead does an app switch, which is very unreliable and jarring for the user when it relaunches the app. This feels like unexpected behaviour. If i instead just run getCurrentAccessToken(), it just gives me a nil value.

It worked perfectly like it was before. Maybe I’m missing something, I can’t quite figure out what the expected solution to this is, with the new v4 of the plugin. 

My mistake on the .init() call.

Have you looked at the Sample app that we ship with Corona SDK for Facebook?

Hi guys,
I whould like to share my work around for this problem -
I notice on ios that while the getAccessToken during the application init returned nil, it return me token few seconds afterwards if the user click on the login button.

So now during the init of the application i try to getAccessToken 3 times with 1 second delay between each call, usually it returns good token on the second attempt.

Hope it can help you also

Yes, I have now tried exactly the Facebook sampe code (with my Facebook app id, and another app Id of a live FB app with many thousands of actual users), and the exact same thing happens :frowning:

HOWEVER - using barak.eliau’s suggestion I actualy got it to work; I experimented and ran the code withing a timer with just 10 milliseconds delay in different iterations, and that gives me a table with the token pretty quickly :slight_smile:

This maybe needs to be reflected in the documentation, that the function needs to be delayed.

Either way,I made a quick code snippet to test this, if it helps people to play around:

local testtime = 10 local curtime = testtime local testTimer = timer.performWithDelay(testtime,function() print("Trying Facebook after time:", curtime) local accessToken = facebook.getCurrentAccessToken() if facebook.isActive == true and accessToken then print("Got access token!") else print("Facebook not active :(") end curtime = curtime + testtime end,10)

I will experiment a bit more, but for now that seems like the solution :slight_smile:

Good find.  Having to run the same delay loop myself.

Is this not locally stored so theoretically access could be quicker?

I have the same issue. Adding a timer doesn´t look like the optional solution specially when this was supported in the previous version. For now I wont migrate fully to facebook v4. But facebook already sent me a message:

 has been making recent API calls to Graph API v2.0, which will reach the end of the 2-year deprecation window on Monday, August 8, 2016. Please migrate all calls to v2.1 or higher in order to avoid potential broken experiences.

I hope we can have a fix for this “issue” before August

Dear Corona Labs

Please update your Facebook sample code, so it works like you intended. You do use the getCurrentAccessToken() in your sample, but it always return nil and creates/ask for a login on every run of the app. 

Now the main reason I would like you to update is I get nothing back from my facebook “me” request, when I only confirm the “login” with  getCurrentAccessToken, but I do get everything I request back, if I use the login function first. However, that creates the unwanted login window at every run like discussed in this thread. 

The wanted behaviour is one login at first run, then silent login, but ability to read multiple other Facebook user values in other app runs. 

To recreate this problem, simply modify line 310 where enforceFacebookLogin() is first called on startup in your Facebook sample code, with a timer, so your code get a valid accessToken back:

timer.performWithDelay( 500, enforceFacebookLogin)

Then Open app, login to facebook, click “Get User”, notice your name is written on screen, close app. Run App again, notice you login, then click “Get User”. Your name is not shown.

 I see no error messages from FBSDK in device console of xcode.

Thanks.

Update: I did modify one more thing, because xcode did previously return an error.

Nov 19 20:50:56 MY-iPhone Facebook[15086] <Notice>: FBSDKLog: starting with Graph API v2.4, GET requests for /me should contain an explicit “fields” parameter

So this should also be updated in your sample code.

facebook.request(“me”, “GET”,  {fields=“id,name”})

What version of the Facebook Sample app are you looking at?  The new public build 2992 has a more modern updated, Facebook sample app.

Rob

I’ve now tested your new version 2.1 Facebook sample, and is happy to report it’s working.

This “new” puppy is what makes the difference.

facebook.setFBConnectListener( listener )

It was not used in version 1.8, so the listener wasn’t initialized on any requests unless a login was made to make it listen.

Btw. even though it’s working, there is still a warning in Xcode, if you don’t fix your “me” request.

Dear Corona Labs

Please update your Facebook sample code, so it works like you intended. You do use the getCurrentAccessToken() in your sample, but it always return nil and creates/ask for a login on every run of the app. 

Now the main reason I would like you to update is I get nothing back from my facebook “me” request, when I only confirm the “login” with  getCurrentAccessToken, but I do get everything I request back, if I use the login function first. However, that creates the unwanted login window at every run like discussed in this thread. 

The wanted behaviour is one login at first run, then silent login, but ability to read multiple other Facebook user values in other app runs. 

To recreate this problem, simply modify line 310 where enforceFacebookLogin() is first called on startup in your Facebook sample code, with a timer, so your code get a valid accessToken back:

timer.performWithDelay( 500, enforceFacebookLogin)

Then Open app, login to facebook, click “Get User”, notice your name is written on screen, close app. Run App again, notice you login, then click “Get User”. Your name is not shown.

 I see no error messages from FBSDK in device console of xcode.

Thanks.

Update: I did modify one more thing, because xcode did previously return an error.

Nov 19 20:50:56 MY-iPhone Facebook[15086] <Notice>: FBSDKLog: starting with Graph API v2.4, GET requests for /me should contain an explicit “fields” parameter

So this should also be updated in your sample code.

facebook.request(“me”, “GET”,  {fields=“id,name”})

What version of the Facebook Sample app are you looking at?  The new public build 2992 has a more modern updated, Facebook sample app.

Rob

I’ve now tested your new version 2.1 Facebook sample, and is happy to report it’s working.

This “new” puppy is what makes the difference.

facebook.setFBConnectListener( listener )

It was not used in version 1.8, so the listener wasn’t initialized on any requests unless a login was made to make it listen.

Btw. even though it’s working, there is still a warning in Xcode, if you don’t fix your “me” request.