How to check if a user likes my Facebook Page or URL using Facebook's API
I tore my hair out over this one too. Your code only works if the user has granted an extended permission for that which is not ideal.
In a nutshell, if you turn on the OAuth 2.0
for Canvas advanced option, Facebook will send a $_REQUEST['signed_request']
along with every page requested within your tab app. If you parse that signed_request you can get some info about the user including if they've liked the page or not.
function parsePageSignedRequest() { if (isset($_REQUEST['signed_request'])) { $encoded_sig = null; $payload = null; list($encoded_sig, $payload) = explode('.', $_REQUEST['signed_request'], 2); $sig = base64_decode(strtr($encoded_sig, '-_', '+/')); $data = json_decode(base64_decode(strtr($payload, '-_', '+/'), true)); return $data; } return false; } if($signed_request = parsePageSignedRequest()) { if($signed_request->page->liked) { echo "This content is for Fans only!"; } else { echo "Please click on the Like button to view this tab!"; } }
You can use (PHP)
$isFan = file_get_contents("https://api.facebook.com/method/pages.isFan?format=json&access_token=" . USER_TOKEN . "&page_id=" . FB_FANPAGE_ID);
That will return one of three:
- string true string false json
- formatted response of error if token
- or page_id are not valid
I guess the only not-using-token way to achieve this is with the signed_request Jason Siffring just posted. My helper using PHP SDK:
function isFan(){ global $facebook; $request = $facebook->getSignedRequest(); return $request['page']['liked'];}
You can do it in JavaScript like so (Building off of @dwarfy's response to a similar question):
<html> <head> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js"></script> <style type="text/css"> div#container_notlike, div#container_like { display: none; } </style> </head> <body> <div id="fb-root"></div> <script> window.fbAsyncInit = function() { FB.init({ appId : 'YOUR_APP_ID', // App ID channelUrl : 'http(s)://YOUR_APP_DOMAIN/channel.html', // Channel File status : true, // check login status cookie : true, // enable cookies to allow the server to access the session xfbml : true // parse XFBML }); FB.getLoginStatus(function(response) { var page_id = "YOUR_PAGE_ID"; if (response && response.authResponse) { var user_id = response.authResponse.userID; var fql_query = "SELECT uid FROM page_fan WHERE page_id = "+page_id+"and uid="+user_id; FB.Data.query(fql_query).wait(function(rows) { if (rows.length == 1 && rows[0].uid == user_id) { console.log("LIKE"); $('#container_like').show(); } else { console.log("NO LIKEY"); $('#container_notlike').show(); } }); } else { FB.login(function(response) { if (response && response.authResponse) { var user_id = response.authResponse.userID; var fql_query = "SELECT uid FROM page_fan WHERE page_id = "+page_id+"and uid="+user_id; FB.Data.query(fql_query).wait(function(rows) { if (rows.length == 1 && rows[0].uid == user_id) { console.log("LIKE"); $('#container_like').show(); } else { console.log("NO LIKEY"); $('#container_notlike').show(); } }); } else { console.log("NO LIKEY"); $('#container_notlike').show(); } }, {scope: 'user_likes'}); } }); }; // Load the SDK Asynchronously (function(d){ var js, id = 'facebook-jssdk'; if (d.getElementById(id)) {return;} js = d.createElement('script'); js.id = id; js.async = true; js.src = "//connect.facebook.net/en_US/all.js"; d.getElementsByTagName('head')[0].appendChild(js); }(document)); </script> <div id="container_notlike"> YOU DON'T LIKE ME :( </div> <div id="container_like"> YOU LIKE ME :) </div> </body></html>
Where the channel.html file on your server just contains the line:
<script src="//connect.facebook.net/en_US/all.js"></script>
There is a little code duplication in there, but you get the idea. This will pop up a login dialog the first time the user visits the page (which isn't exactly ideal, but works). On subsequent visits nothing should pop up though.