Why is Facebook PHP SDK getUser always returning 0?
Asked Answered
S

26

39

I'm trying to work with a website that requires some information from a Facebook user, I'm using PHP and JS SDKs.

I have a function in PHP:

public function isLoggedOnFacebook() {
    $user = $this->_facebook->getUser();
    if ($user) {
        return $this->_facebook->api("/$user");
    }
    return false;
}

On a class that is holding the facebook object from the SDK in $this->_facebook.

Then on a block I do this:

<?php if (!$this->isLoggedOnFacebook()): ?>
<div>
   <fb:login-button show-faces="true" perms="email" width="500" />
</div>
<?php endif ?>

And the FB JS environment is properly set up (I think) so it works. So the user gets the pop up and authorizes the site.

The problem is even after the app is been authorized by the user $user is always 0, meaning $facebook->getUser() always returns 0, and then lists the faces of users, including the logged user, but if I make it call $facebook->api('/me') or whatever, then it'll throw the invalid token exception.

I've seen this problem, but I haven't seen a solution, I have no idea where the problem is and I run out of ideas.

There's a Website tab on the developers' Facebook page in the apps section, where you can set up your Site URL and your Site Domain, and I'm thinking this are the cause of my problem, but I have no knowledge of exactly what these fields are supposed to contain.

Suavity answered 22/7, 2011 at 12:50 Comment(5)
To answer my own question, I've found that the current JS SDK is not compatible with the PHP SDK 3.0.0. There should be a new JS SDK released soon, but it's not online yet, so that's the reason it doesn't work.Suavity
look at this: How to properly handle session and access token with Facebook PHP SDK 3.0?.Hershberger
I'm also having the getUser() == 0 problem with the 3.0.1 PHP API!Hoyle
@Suavity Are you planning on picking an answer here?Weakwilled
Well, all answers have relevant information, as I said in my previous comment, this particular problem was caused because for a period of time (now gone) the SDKs provided by facebook were not compatible with each other. Now for future reference I pick the nice blog post cause I think is quite clear in how it all works.Suavity
S
0

The answer to my specific issue was that there were incompatibilities between the versions of the JS SDK and PHP SDK I was using and just upgrading them solved it.

The symptom of this issue is similar when it's caused by a variety of different things so you may do very well in scouting through the different answers available in this page.

Suavity answered 9/6, 2016 at 14:43 Comment(0)
O
23

I had the same problem and I figured it out that is because SDK uses the variable $_REQUEST and in my environment is not true that is merged with $_GET, $_POST and $_COOKIE variables.

I think it depends on the PHP version and that is why someone made it work by enabling cookies.

I found this code in base_facebook.php:

protected function getCode() {
    if (isset($_REQUEST['code'])) {
        if ($this->state !== null &&
                isset($_REQUEST['state']) &&
                $this->state === $_REQUEST['state']) {

            // CSRF state has done its job, so clear it
            $this->state = null;
            $this->clearPersistentData('state');
            return $_REQUEST['code'];
        } else {
            self::errorLog('CSRF state token does not match one provided.');
            return false;
        }
    }

    return false;
}

And I modified it as you can see below by creating $server_info variable.

protected function getCode() {
    $server_info = array_merge($_GET, $_POST, $_COOKIE);

    if (isset($server_info['code'])) {
        if ($this->state !== null &&
                isset($server_info['state']) &&
                $this->state === $server_info['state']) {

            // CSRF state has done its job, so clear it
            $this->state = null;
            $this->clearPersistentData('state');
            return $server_info['code'];
        } else {
            self::errorLog('CSRF state token does not match one provided.');
            return false;
        }
    }

    return false;
}
Origen answered 7/11, 2012 at 21:4 Comment(10)
this worked for me as well. Hate to change the library but it works. This was on a codeigniter installation if that helps anybody.Peanuts
holy smokes, this solved getUser() === 0 problem. Also codeigniter.Mediaeval
Thanks!! I wasted about a day trying to debug this. Ended up recreating the superglobal array in my controller's constructor: function __construct() { parent::__construct(); $_REQUEST = array_merge($_GET, $_POST, $_COOKIE); }Faludi
This fix also worked for me, on a Code igniter installation. This might may be unique to CI...Tania
I had this issue with my CodeIgniter 2 app and Only this solution solved my problem after endless searching for getUser() returning 0. I was reluctant to edit the library, but finally only this solution solved my problem.Absquatulate
you dont have to change getCode() function if you add 'cookie' => true in your facebook configMould
@ArifRH, not true. With 'cookie' => true it still doesn't work.Dannettedanni
@alexg, you don't have to edit the library. Just do $_REQUEST = array_merge($_GET, $_POST, $_COOKIE); before using the library.Dannettedanni
@Dannettedanni I did not edit the library, I inserted code to recreate the arrays in my CodeIgniter controller's constructor, which runs before using the FB library, as you suggested. It seems everyone who comes here is using CodeIgniter.Faludi
@alexg, oh yeah, you're right. I guess my comment was meant for Norberto Yoan.Dannettedanni
H
5

I ran into similar problem. $facebook->getUser() was returning 0 and sometimes it returned valid user id when user wasn't actually logged in, resulting in Fatal Oauth error when I tried to make graph api calls. I finally solved this problem. I don't know if it is the right way but it works. Here is the code :

<?php
include 'includes/php/facebook.php';
$app_id = "APP_ID";
$app_secret = "SECRET_KEY";
$facebook = new Facebook(array(
    'appId' => $app_id,
    'secret' => $app_secret,
    'cookie' => true
));

$user = $facebook->getUser();

if ($user <> '0' && $user <> '') { /*if valid user id i.e. neither 0 nor blank nor null*/
try {
// Proceed knowing you have a logged in user who's authenticated.
$user_profile = $facebook->api('/me');
} catch (FacebookApiException $e) { /*sometimes it shows user id even if user in not logged in and it results in Oauth exception. In this case we will set it back to 0.*/
error_log($e);
$user = '0';
}
}
if ($user <> '0' && $user <> '') { /*So now we will have a valid user id with a valid oauth access token and so the code will work fine.*/
echo "UserId : " . $user;

$params = array( 'next' => 'http://www.anujkumar.com' );
echo "<p><a href='". $facebook->getLogoutUrl($params) . "'>Logout</a>";

$user_profile = $facebook->api('/me');
echo "<p>Name : " . $user_profile['name'];
echo "<p>";
print_r($user_profile);

} else {/*If user id isn't present just redirect it to login url*/
header("Location:{$facebook->getLoginUrl(array('req_perms' => 'email,offline_access'))}");
}

?>
Honan answered 11/11, 2011 at 8:27 Comment(1)
Hi Anuj, thank you for code. There is one problem though whenever I successfully login first time, 2nd time it does not work and it shows 500 Error Internal server error. Any idea?Disharmonious
H
4

Check out this blog post: http://thinkdiff.net/facebook/new-javascript-sdk-oauth-2-0-based-fbconnect-tutorial/

New JS SDK has been released - https://developers.facebook.com/blog/post/525

Heresiarch answered 23/7, 2011 at 22:52 Comment(2)
Please summarize the blog post here? If the link goes dead we've got nothing.Vip
I understand Todds opinion, I've accepted this answer because the blog was the most complete information, it's just a tutorial, and it's actually different now than in 2011. My problem (I am the one who asked the question) was originated by conflicting js and php sdks versions. The problem seems to be caused by a huge variety of issues, this is why lots of answers are applicable and I thought a thorough look at all the details was an appropriate answer.Suavity
C
3

You need to ensure that your app is set to pick up the code parameter from the Query String rather than the uri_fragment, this can be set on facebook apps page apps>settings>permissions.

That did it for me using $facebook->getLoginUrl() to provide the login URL.

Creamcolored answered 25/10, 2012 at 16:7 Comment(0)
W
2

Check your config array. Ensure that you are using proper string encaps quotes when setting the values.

$config = array();
$config["appId"] = $APP_ID;
$config["secret"] = $APP_SECRET;
$config["fileUpload"] = false; // optional

This works.

$config = array();
$config[‘appId’] = 'YOUR_APP_ID';
$config[‘secret’] = 'YOUR_APP_SECRET';
$config[‘fileUpload’] = false; // optional

This is a direct copy/paste from the website http://developers.facebook.com/docs/reference/php/ and does NOT work because of the odd squiggly quotes.

the long answer is that your hash for your "checking" of the app signature is not coming out to a correct check, because the app secret is not returning a valid value (it's returning nothing, actually)... so the hash_hmac function is returning an incorrect value that doesn't match properly, etc...

Weakwilled answered 9/4, 2012 at 7:5 Comment(1)
Just saved my life I'm so stupid they indeed put wrong quotes and I copy/pasted it!Lid
C
2

After debugging through the base_facebook.php I found, because somehow I had lost my .crt file the access token is forever invalid. Make sure you have your fb_ca_chain_bundle.crt available at: https://github.com/facebook/facebook-php-sdk/blob/master/src/fb_ca_chain_bundle.crt

Collusive answered 28/4, 2013 at 20:56 Comment(1)
This WORKS!!!! Thanks a lot!!!!! Finally (three days) some clue!!! Just make sure you have base_facebook.php, facebook.php and fa_ca_chain_bundle.crt in the same directory. Check the .php files start with /** * Copyright 2011 Facebook, Inc. * and the .crt with ## ## ca-bundle.crt -- Bundle of CA Root Certificates ## ## Certificate data from Mozilla as of: Thu Oct 18 19:05:59 2012Auschwitz
B
2

Hours and hours down the drain. None of the posts about this on Stack Overflow or other sites provided the solution to my problem. I finally went in to the library code and figured out exactly where it was dying.

On my development machine, which uses XAMPP for Windows, I kept getting the 0 for logging in, while my test server would work properly. After realizing an exception was being thrown but hidden, I put an $e->getMessage() in base_facebook.php, which pointed out I was having an SSL error. The following post, HTTPS and SSL3_GET_SERVER_CERTIFICATE:certificate verify failed, CA is OK, led me to a solution.

The solution:

In base_facebook.php, add the following before curl_exec($ch):

curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);

You should probably wrap the above in whatever flags you use to determine if you are in development mode, because you won't want the above line in a production system. For instance:

if ( getenv( 'environment' ) === 'development' ) {
    curl_setopt( $ch, CURLOPT_SSL_VERIFYPEER, false );
}
Buchenwald answered 11/10, 2013 at 16:51 Comment(0)
F
1

I checked and test a long time, Now I found the reason.

Please login developer apps, in settings-->Advance-->Migrations-->Deprecate offline access-->disabled.

You will find $facebook->getUser() will work.

another thing. had better add domain when new the facebook class;

$facebook = new Facebook(array(
'appId' => APP_ID,//$app_id,
'secret' => APP_SECRET,//$app_secret,
'cookie' => true,
'domain'=>'xxxdomain.com',
));
$session = $facebook->getUser();    
Flexuosity answered 15/3, 2012 at 20:41 Comment(0)
K
1

Try this in your piece of code: on if condition true you'll be reirected to facebook then login yourself and i hope you'll good to go by then but remember use new libraries of php SDK

if(($facebook->getUser())==0)
{
 header("Location:{$facebook->getLoginUrl(array('scope' => 'photo_upload,user_status,publish_stream,user_photos,manage_pages'))}");
 exit;
}
else {
$accounts_list = $facebook->api('/me/accounts');
echo "i am connected";
}
Karlsbad answered 1/5, 2012 at 18:21 Comment(0)
L
1

I was having the exact same problem on my Facebook app, and I finally figured it out after 2 days of hair pulling frustration. It turned out to be an issue with the redirect-uri in the getLoginUrl()! if it doesn't match the registered app domain through facebook, they return the error, and the user gets returned as 0 (the default user value).

Lanoralanose answered 7/5, 2012 at 23:50 Comment(0)
N
1

i solved this as i faced the same problem. Just goto developers.facebook.com/apps then navigate to your app hit EDIT APP button

IF you have check "App on facebook" and have entered a canvas url to it the app will not work out side the facebook will work under apps.facebook.com/

just remove this check it worked for me

Nonu answered 12/5, 2012 at 17:15 Comment(0)
E
1

$facebook->getUser() will return 0, if the user doesn't authenticate the app.

use $facebook->getLoginUrl to get the URL to authenticate the app.

Ensign answered 15/5, 2012 at 5:23 Comment(0)
D
1
<?php

require 'facebook.php';

// Create our application instance
// (replace this with your appId and secret).
$facebook = new Facebook(array(
  'appId'  => 'YOUR_APP_ID',
  'secret' => 'YOUR_APP_SECRET',
));

// Get User ID
$user = $facebook->getUser();

// We may or may not have this data based 
// on whether the user is logged in.
// If we have a $user id here, it means we know 
// the user is logged into
// Facebook, but we don’t know if the access token is valid. An access
// token is invalid if the user logged out of Facebook.

if ($user) {
  try {
    // Proceed knowing you have a logged in user who's authenticated.
    $user_profile = $facebook->api('/me');
  } catch (FacebookApiException $e) {
    error_log($e);
    $user = null;
  }
}

// Login or logout url will be needed depending on current user state.
if ($user) {
  $logoutUrl = $facebook->getLogoutUrl();
} else {
  $loginUrl = $facebook->getLoginUrl();
}

// This call will always work since we are fetching public data.
$naitik = $facebook->api('/naitik');

?>
<!doctype html>
<html xmlns:fb="http://www.facebook.com/2008/fbml">
  <head>
    <title>php-sdk</title>
    <style>
      body {
        font-family: 'Lucida Grande', Verdana, Arial, sans-serif;
      }
      h1 a {
        text-decoration: none;
        color: #3b5998;
      }
      h1 a:hover {
        text-decoration: underline;
      }
    </style>
  </head>
  <body>
    <h1>php-sdk</h1>

    <?php if ($user): ?>
      <a href="<?php echo $logoutUrl; ?>">Logout</a>
    <?php else: ?>
      <div>
        Login using OAuth 2.0 handled by the PHP SDK:
        <a href="<?php echo $loginUrl; ?>">Login with Facebook</a>
      </div>
    <?php endif ?>

    <h3>PHP Session</h3>
    <pre><?php print_r($_SESSION); ?></pre>

    <?php if ($user): ?>
      <h3>You</h3>
      <img src="https://graph.facebook.com/<?php echo $user; ?>/picture">

      <h3>Your User Object (/me)</h3>
      <pre><?php print_r($user_profile); ?></pre>
    <?php else: ?>
      <strong><em>You are not Connected.</em></strong>
    <?php endif ?>

    <h3>Public profile of Naitik</h3>
    <img src="https://graph.facebook.com/naitik/picture">
    <?php echo $naitik['name']; ?>
  </body>
</html>
Diffusion answered 15/5, 2012 at 9:30 Comment(0)
I
1

I had same problem with getUser(), It returns 0 in IE 8. I found a solution after doing some research. Follow the link below. This worked like a charm.

http://www.andugo.com/facebook-php-sdk-getuser-return-0-value-on-ie/

Irretentive answered 6/7, 2012 at 1:19 Comment(1)
This just fixed it for me. Wtf, how am I supposed to figure these weird facebook api issues out ?? Every little piece of FB api takes hours to debug..Thing
A
1

After some desperate hours, here is what caused the same issue on my server: If you use SSL, make sure that port 443 is not blocked! I opened the port last year, but it appeared that my webhoster somehow did a reset recently.

Abilene answered 22/8, 2013 at 21:16 Comment(0)
T
0

If you use the new SDK 3.1.1 and JS you need to add new variable to FB.init routine called

oauth : true to use the new OATH 2.0 Protocol ! Then update your login button while perms are not allowed please use scope instead of perms

Townswoman answered 21/9, 2011 at 16:9 Comment(0)
A
0

getUser() and PHP-SDK silently fails if _REQUEST like globals dropping by http server by misconfiguration. I was using wrong-configured nginx and after tracing code ~3 hours solved this problem via vhost configuration change.

I wrote a comment about solution here: https://github.com/facebook/php-sdk/issues/418#issuecomment-2193699

I hope helps.

Asthenosphere answered 28/9, 2011 at 22:58 Comment(3)
Comment is not longer there on Github :(Keele
yes, i think issue is deleted or moved elsewhere with at least 50+ comments. my problem was related with few empty _SERVER globals which served by nginx.Asthenosphere
I solved this by putting this following code above the library load. parse_str($_SERVER['QUERY_STRING'],$_REQUEST);Colyer
A
0

A facebook->getUser() will return 0 when there is no logged-in user. (https://developers.facebook.com/docs/reference/php/facebook-getUser/)

To resolve this, the Facebook JS SDK provides an access token from a successful login which you can use with the Facebook PHP SDK.

The javascript below will check whether or not a Facebook login already exists and your Facebook App is authorized:

FB.getLoginStatus(function($response) {
    if ($response.status === 'connected') {
        var uid = $response.authResponse.userID;
        var accessToken = $response.authResponse.accessToken;
        _accessServer(uid, accessToken);

    } else if ($response.status === 'not_authorized') {
        _loginPopup();

    } else {
        _loginPopup();
    }
});

The function _accessServer opens another request back to your server, sending the access token.

The function _loginPopup should open the Facebook login popup requesting the appropriate permissions for the user to "allow access" to your application.

The PHP application should then pass the access token back to the Facebook API:

$facebook->setAccessToken($new_access_token);
$uid = $facebook->getUser();

https://developers.facebook.com/docs/reference/php/facebook-setAccessToken/

Hope that helps.

Ailee answered 18/8, 2012 at 2:53 Comment(0)
T
0

Adding this line solved this problem for me in IE9:

header('P3P:CP="IDC DSP COR ADM DEVi TAIi PSA PSD IVAi IVDi CONi HIS OUR IND CNT"'); // This is the main cause to use on IE.
Thing answered 21/8, 2012 at 11:51 Comment(0)
G
0

If this question is still relevant to people, I'd like to contribute my 2 cents as I struggled quite some time to get things working.

First of all, try out the SDK that would suit you, whether it be PHP or JS. In essence they both do the same stuff, it's just that JS might handle it a bit more elegant (with the pop-up dialog and what not). There's a lot of different tutorials, manuals and examples out there! It took me like a week to find 1 that suited me and that I could actually use. Once you've found the piece of code that works with the SDK you plan on using, it's time for you to alter the code to your specific needs.

Once I had finished my code, I started testing it. I noticed I was running my code on localhost, and I too was getting no result from my arrays. To answer your question: upload your code to a (sub)domain and try again. My code worked all the time, but because I did not have it online, it didn't work. If you already got it online, then my answer is not of use to you.

I'm sorry if this kind of small story isn't really meant to be on SO, but it might help people.

Good luck!

Glucoside answered 29/3, 2013 at 9:52 Comment(0)
C
0
    if ($facebook->getUser()) {
       $userProfile = $facebook->api('/me');
       // do logic
    } else {
       $loginUrl = $facebook->getLoginUrl($params = array('scope' => SCOPE));
       header('Location:' . $loginUrl);
    }

that how i fixed my problem, now it is returning me the detail of user profile for further processing. (it was such a headache)

Custody answered 8/5, 2013 at 6:50 Comment(1)
sidenote: remember to call exit; after header('Location: $url');Albina
D
0

These are good suggestions but the thing that worked for me is on Facebook itself. After refactoring the code many times I realized it's a problem with the configurations on Facebook.
The following steps resolved my issue.

1.) Under Basic > App on Facebook... I deselected that although you can leave it if you want

2.) Under Permissions > Privacy -> set to Public

Permissions > Auth Token -> set to Query String

3.) Under Advanced -> Authentication > App Type -> Web

The third step is the one that really fixed it all, not completely sure why though, hope that helps

Desired answered 23/6, 2013 at 16:37 Comment(0)
C
0

Make sure you call this Facebook API-function getUser before any output, because it uses Session variables and Cookies. Headers can not be sent/read correctly if you did.

Coign answered 11/8, 2013 at 18:33 Comment(0)
C
0

I also spent many hours looking at this and also found a solution. Might not be for you but it seems there is some issue with $_SERVER['QUERY_STRING'] so you need to set it into the $_REQUEST array.

I was using codeigniter and found that the following code above the library load worked.

parse_str($_SERVER['QUERY_STRING'],$_REQUEST);

    parse_str($_SERVER['QUERY_STRING'],$_REQUEST);
    $config = array(); 
    $config["appId"] = "63xxxxx39";
    $config["secret"] = "dexxxx3bf";
    $this->load->library('facebook',$config);

    $this->user = $user = $this->facebook->getUser();
    if ($user) {

        try {
                // Proceed knowing you have a logged in user who's authenticated.
                $user_profile = $this->facebook->api('/me');
                //print_r($user_profile);exit;
        } catch (FacebookApiException $e) {
                echo '<pre>'.htmlspecialchars(print_r($e, true)).'</pre>';
                $user = null;
        }
        $logout = $this->facebook->getLogoutUrl();
        $this->fb_logout = $logout;
        $this->fb_user = $user_profile;

    } else {
        $login = $this->facebook->getLoginUrl(array("scope"=>"email","redirect_uri"=>"http://domain/login/login_fbmember/"));
        $this->fb_login = $login;
    }

}
Colyer answered 23/1, 2014 at 11:36 Comment(0)
A
0

This issue is really weird. I have discovered that the problem was the static $CURL_OPTS array in the base_facebook.php.

Try to edit it from this:

  /**
   * Default options for curl.
   *
   * @var array
   */
  public static $CURL_OPTS = array(
    CURLOPT_CONNECTTIMEOUT => 10,
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_TIMEOUT        => 60,
    CURLOPT_USERAGENT      => 'facebook-php-3.2',
  );

to

  /**
   * Default options for curl.
   *
   * @var array
   */
  public static $CURL_OPTS = array(
    CURLOPT_CONNECTTIMEOUT => 10,
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_TIMEOUT        => 60,
    CURLOPT_USERAGENT      => 'facebook-php-3.2',
    CURLOPT_IPRESOLVE => CURL_IPRESOLVE_V4 
  );
Alyssa answered 11/11, 2015 at 13:44 Comment(0)
S
0

The answer to my specific issue was that there were incompatibilities between the versions of the JS SDK and PHP SDK I was using and just upgrading them solved it.

The symptom of this issue is similar when it's caused by a variety of different things so you may do very well in scouting through the different answers available in this page.

Suavity answered 9/6, 2016 at 14:43 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.