Facebook SDK - Using JS to Auth and PHP for the rest? - facebook

I am trying to use the Facebook PHP and JS SDKs together in order to create a web app that will double as a canvas app. In the current setup I am experiencing issues when the page is left or a while and the system reverts back to the login screen. It is important to not I am using a dynamic domain mapper and there are a few possible URLs /dev/, /dev/pool/, /dev/pool/edit/, etc. that the user might visit and experience the app.
I read around and found that authorizing with the JS SDK is the correct method (I could be wrong?) and then using the PHP SDK to sort through everything else will work just find, gaining the access token naturally.
I know this is something wrong with my authentication setup, as I see it reload sometimes, I also get stuck with a login button that doesn't do anything if I am on a sub page, and if I don't touch the site for a couple of minutes the system tries to re-auth for no reason.
Any ideas as to what I am doing wrong?
Thanks!
Here is the JS set up on my site:
<div id="fb-root"></div>
<script>
window.fbAsyncInit = function() {
FB.init({
appId: 'XXXXX',
channelUrl: 'http://www.domain.com/channel.php',
status: true,
cookie: true,
xfbml: true,
oauth: true,
});
FB.Event.subscribe('auth.login', function(response) {
alert('refreshing')
window.location.reload();
});
FB.Event.subscribe('auth.logout', function(response) {
window.location.reload();
});
FB.Canvas.setSize({ width: 810 });
FB.Canvas.setAutoGrow();
};
(function(d, debug){
var js, id = 'facebook-jssdk', ref = d.getElementsByTagName('script')[0]
if (d.getElementById(id)) {return;}
js = d.createElement('script'); js.id = id; js.async = true;
js.src = "//connect.facebook.net/en_US/all" + (debug ? "/debug" : "") + ".js";
ref.parentNode.insertBefore(js, ref);
}(document, /*debug*/ true));
</script>
Here is the PHP flow of calling the Facebook Object
$fb = new FbDoa();
if ($fb->isAuthed() === false) {
echo $fb->getLoginButton();
}
else {
echo $fb->getProfileInfo();
}
Here is the PHP contents of the FbDoa Object ($fb):
public function __construct() {
require_once(Facebook/facebook.php');
$this->facebook = new Facebook(array(
'appId' => 'XXXXX',
'secret' => 'XXXXXXXXXX',
'cookie' => true,
));
$this->user = $this->facebook->getUser();
if ($this->user) {
try {
// Proceed knowing you have a logged in user who's authenticated.
$this->user_profile = $this->facebook->api('/me');
} catch (FacebookApiException $e) {
//echo '<pre>'.htmlspecialchars(print_r($e, true)).'</pre>';
$this->user = null;
}
}
}
public function isAuthed() {
if ($this->user) {
return true;
}
else {
return false;
}
}
public function getLoginButton() {
$scope = 'email,user_likes,friends_likes,publish_actions,publish_stream,read_friendlists';
return '<fb:login-button size="xlarge" perms="'.$scope.'"></fb:login-button>';
}
public function getProfileInfo() {
return $this->user_profile;
}
UPDATE 1:
It really seems like window.location.reload(); is not doing anything, if I hit the login button over and over nothing happens, but I refresh it works. That being true the app's auth should last longer than a couple mins, which means there are a few issues before me. Any ideas?
UPDATE 2:
The issue could be with my server-side code? anyone know anything about PHP+JS SDK?

The signed request is saved in a cookie similar to fbsr_appid. From that you can use the code to deal with it. Here is how your flow should look
As long as there is a base url in your app settings it should redirect to all.

Related

Problems handling response.status in auth.authResponseChange event

I want to create a login system that can also use FB's login. So I've setup the FB object and SDK in my page and then subscribed to the auth.authResponseChange event and added an anonymous function to do stuff if I'm logged, not logged or not authorized.
When I'm logged it works properly. When I'm not logged or not authorized, it does nothing. I think it just doesn't enter into the anonymous function either, because I've put a console.log() before the if and it does nothing.
Here's my code:
// Facebook stuff
window.fbAsyncInit = function()
{
FB.init({
appId : 'my id blabla', // App ID
channelUrl : 'my channel.html bla bla', // Channel File
status : true, // check login status
cookie : true, // enable cookies to allow the server to access the session
xfbml : true // parse XFBML
});
FB.Event.subscribe('auth.authResponseChange', function(response)
{
console.log("Running function");
if(response.status === "connected")
{
console.log("Connected and authorized");
}
else if (response.status === 'not_authorized')
{
console.log("Not authorized");
}
else
{
console.log("Not connected");
}
});
};
// Load the SDK asynchronously
(function(d)
{
var js, id = 'facebook-jssdk', ref = d.getElementsByTagName('script')[0];
if (d.getElementById(id)) {return;}
js = d.createElement('script'); js.id = id; js.async = true;
js.src = "//connect.facebook.net/en_US/all.js";
ref.parentNode.insertBefore(js, ref);
}(document));
I have the same problem, but for what it's worth if you subscribe to the event 'auth.statusChange' instead of 'authResponseChange' you can know if he is 'connected' to facebook and authorized your app or if he's connected to fb but not authorized.
Also if you use the FB.getLoginStatus, which facebook advise not to, you can know in what of the three states (connected, not_autorized or not_connected) the user is in.

Login using facebook, error occurs after log in and allowing app for basic permissions

Error obtained is An error occurred, please try again later
I created new facebook app and go the APP ID. I entered domain name as blogspot.in and redirect URL as my blog
I then used the below code from
<div id="fb-root"></div>
<script>
window.fbAsyncInit = function() {
FB.init({
appId : 'YOUR_APP_ID',
status : true,
cookie : true,
xfbml : true,
oauth : true,
});
};
(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 class="fb-login-button">Login with Facebook</div>
I entered this code in my blog using Javascript/HTML gadget and everything works fine till logging in and allowing the app, after that i'm getting the error.
I even tried this using localhost by changing the 127.0.0.1 to local.localhost in hosts file but even in that i'm getting the same error. i went through many stackoverflow posts and nothing helped.
My questions are;
can we use login using facebook in blogger
If so, whats the problem and how to correct it?
Imp: You can view the error by going to my blog and in right side you can see login with facebook option(Don't worry nothing happens by logging in, I'm just using it for testing)
The facebook button with provide a way to facilitate users to login via facebook. In this way user grant facebook access to your website and once grant access completed, facebook will send you user data. You must use such data to process, authorize, auto login, auto signup user. it can't be done directly but needed additional steps internally in your website or blog website.
Follow the following approach while implementing facebook login / auto sign up process in your website using facebook login button.
i: page script.
<script>
window.fbAsyncInit = function () {
FB.init({ appId: 'appid', status: true, cookie: true,
xfbml: true
});
};
(function () {
var e = document.createElement('script'); e.async = true;
e.src = document.location.protocol +
'//connect.facebook.net/en_US/all.js';
document.getElementById('fb-root').appendChild(e);
} ());
ii: create link and call facebook function when using click on login button. e.g
<a rel="nofollow" href="javascript:void(0);" onclick="fb_login();">login to facebook</a>
iii: create fb_login() function
function fb_login() {
FB.login(function (response) {
if (response.authResponse) {
// user authorized
Process_Login(u, redirect);
} else {
console.log('User cancelled login or did not fully authorize.');
}
}, { scope: 'email,user_birthday,user_hometown,publish_stream' });
}
// this function is responsible for sending data retrieved from facebook to your website via ajax for authorization, auto login, auto registration purpose.
function Process_Login() {
FB.api('/me', function (response) {
var fb_data = "uid=" + response.id + "&fn=" + response.first_name + "&ln=" + response.last_name + "&gn=" + response.gender + "&bt=" + response.birthday + "&eml=" + response.email;
if (response.hometown != undefined)
fb_data = fb_data + "&loc=" + response.hometown.name;
if (response.username != undefined)
fb_data = fb_data + "&uname=" + response.username;
$.ajax({
type: 'GET',
url: u + "handlers/signup.ashx",
data: fb_data,
success: function (msg) {
// login process completed
// redirect user to final page.
}
});
});
}

Facebook oauth failure after recent FB SDK changes

After a rather frustrating bout with Facebook OAuth 2, and having my Facebook Connect login break completely on my site (www.thegameeffect.com), I'm turning to the wise minds of StackOverflow in hope of some guidance.
Things were working rather nicely as of a 1-2 months ago, but recently I've been having problems. Basically, I have followed the steps according to the FB developers site, and hit several other help guides from here, such as this link: (http://stackoverflow.com/questions/8537007/facebook-cookie-and-oauth-2-0-changes) and have sadly not had any luck.
My FB.Init code looks like below:
<div id="fb-root"></div>
<script type="text/javascript">
window.fbAsyncInit = function () {
FB.init({ appId: '145290112183820', status: true, cookie: true, xfbml: true, channelUrl: 'http://www.thegameeffect.com/fbchannel.html' });
//, oauth:true
};
(function () {
// 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);
var e = document.createElement('script'); e.async = true;
e.src = document.location.protocol + '//connect.facebook.net/en_US/all.js#xfbml=1';
document.getElementById('fb-root').appendChild(e);
} ());
</script>
I have tried all variations of this, with oauth:true included, the channelurl excluded, the self invoking function with the top part uncommented, and still all that happens when I try to log in is the auth window pops up briefly, and then disappears. The code that gets executed when you click on the FB icon in the top left of the header is below:
FB.login(function (response) {
if (response.session) {
// do server side work (this never gets hit)
}
});
Any suggestions?
Some minor changes will make your code work :
window.fbAsyncInit = function () {
FB.init({ appId: '145290112183820', status: true, cookie: true,
xfbml: true, channelUrl:
'http://www.thegameeffect.com/fbchannel.html', oauth: true });
};
and
FB.login(function (response) {
if (response.authResponse) {
}
});
So, after a bit more digging, and a lot of debugging, I finally found the solution. I was able to get the javascript side of things working thanks to manishekhawat, and the server side thanks to this awesome post:
http://amirrajan.net/Blog/facebook-oauth-authentication-and-iframe-apps
For anyone having problems with the new Facebook oAuth cookie in ASP.NET, this is an amazing tutorial!
Thanks again for the help today; I'm glad to finally have everything in working order.
Change,
FB.getLoginStatus(function(response) {
if (response.session) { ........................
}
by
FB.getLoginStatus(function(response) {
if (response.authResponse) {
........................
}
My facebook app make Infinite loop in sdk 3.1.1

FB.Event.subscribe('auth.login') won't trigger everytime ?

<div id="fb-root"></div>
<script>
window.fbAsyncInit = function() {
FB.init({
appId : 'MY_APP_ID',
status : true,
cookie : true,
xfbml : true
});
FB.Event.subscribe('auth.login', function(response) {
$.ajax({
url: "http://example.com/fbconnect",
success: function(){
window.location.reload();
}
});
});
};
(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 class="fb-login-button" data-perms="email,user_birthday,user_hometown,user_location">Login with Facebook</div>
It's working with only two cases.
1- when a user is NOT logged in and log in to facebook it triggers.
2- when a user is logged in but didn't authorize the app yet it triggers.
the third scenario which is not working is when a user is logged in and He is already authorized the app the FB.Event.subscribe('auth.login) won't trigger !!!
I encountered the same thing as you and I found a function, "getLoginStatus", that might be of interest for you.
When the user is already logged in and has granted your app all the permissions, then there is no need to log in again and therefore the event won't be triggered.
However, if the response of the "getLoginStatus" is "connected" you can do the stuff you want to do when the user is already logged in and has granted your app all the permissions.
The complete script might look something like this:
<script>
window.fbAsyncInit = function() {
FB.init({
appId : 'APPID', // App ID
channelUrl : 'CHANNEL_URL', // 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) {
if (response.status === 'connected') {
// the user is logged in and connected to your
// app, and response.authResponse supplies
// the user's ID, a valid access token, a signed
// request, and the time the access token
// and signed request each expire
var uid = response.authResponse.userID;
var accessToken = response.authResponse.accessToken;
FB.api('/me', function(response) {
if (response.name != undefined ) {
console.log("Welcome, " + response.name);
}
});
} else if (response.status === 'not_authorized') {
// the user is logged in to Facebook,
// but not connected to the app
} else {
// the user isn't even logged in to Facebook.
}
});
// Additional initialization code here
};
// 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>
Got the exact same issue here and it's driving me nuts. Not liking the Facebook Javascript SDK atm.
It's really complex with the status check in FB.init() and makes it even harder when you put facebook comments on the page...
A workaround I just tested is to have your own login button and use the FB.login() method, there you can hook in to the callback (this replaces your code for the auth.login event).
window.fbAsyncInit = function () {
FB.init({
...
});
$('#fb-login-button-custom').show().click(function () {
var scopeList = $(this).data('scope');
FB.login(function (response) {
alert('FB.login callback');
console.log(response);
document.location.href = document.location.pathname + '?fblogin=1';
}, { scope: scopeList });
});
});
That default login event is actually only triggered when the user authorizes your application. So when loging out the user, you could revoke the authorization. But then every time they log in they have to 'allow' the app.
Using FB.Event.subscribe('auth.statusChange', handleStatusChange); will notify you status changes..
hope it helps

facebook app reloading in loop, login logout events getting fired automatically inside window.fbAsyncInit

I am developing a facebook (iframe) app.
I have included following code at bottom of my page:
<script>
window.fbAsyncInit = function() {
FB.Canvas.setAutoResize();
FB.init({
appId : '<?php echo FACEBOOK_APP_ID; ?>',
session : '<?php echo json_encode($session); ?>',
status : true,
cookie : true,
xfbml : true
});
// whenever the user logs in / out, we refresh the page
FB.Event.subscribe('auth.login', function() {
window.location.reload();
});
FB.Event.subscribe('auth.logout', function() {
window.location.reload();
});
};
(function() {
var e = document.createElement('script');
e.src = document.location.protocol + '//connect.facebook.net/en_US/all.js';
e.async = true;
document.getElementById('fb-root').appendChild(e);
}());
</script>
The problem here is, it seems that auth.login and auth.logout events are getting fired immediately inside window.fbAsyncInit function, even if I do not log-out from (or log-in to if logged out) my facebook profile.
I am doing no such action, even then these events seem to get fired, which causes their handler functions to reload my app (window.location.reload();), and the app goes into infinite reload loop.
Please guide me.
Thanks
From my experience instead of using auth.logout and auth.login events you may try the following code:
FB.Event.subscribe('auth.authResponseChange', function(response) {
FB.getLoginStatus(function(response) {
if (response.status === 'connected') {
// the user is logged in and connected to your
// app, and response.authResponse supplies
// the user's ID, a valid access token, a signed
// request, and the time the access token
// and signed request each expire
var uid = response.authResponse.userID;
var accessToken = response.authResponse.accessToken;
} else if (response.status === 'not_authorized') {
// the user is logged in to Facebook,
//but not connected to the app
} else {
// the user isn't even logged in to Facebook.
}
});
});
I've been stuck trying to solve this bug for a few days. The thing is that auth.login event is fired when the SDK is loaded even if you're already connected thus creating an infinite loop. I've solved it when i made the code listen to the authlogin event and reloading the page only if the user is not connected.
<script type="text/javascript">
window.fbAsyncInit = function() {
FB.init({
appId : '<?php echo AppInfo::appID(); ?>', // App ID
channelUrl : '//<?php echo $_SERVER["HTTP_HOST"]; ?>/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
});
// Listen to the auth.login which will be called when the user logs in
// using the Login button
FB.getLoginStatus(function(response) {
console.log (response.status);
//this is useful if you want to avoid the infinite loop bug
//it only reloads page when you log in
if (response.status != 'connected') {
FB.Event.subscribe('auth.login', function(response) {
// We want to reload the page now so PHP can read the cookie that the
// Javascript SDK sat. But we don't want to use
// window.location.reload() because if this is in a canvas there was a
// post made to this page and a reload will trigger a message to the
// user asking if they want to send data again.
//window.location = window.location;
//Im using the window.location.reload()
window.location.reload();
});
}
});
FB.Canvas.setAutoGrow();
};
// Load the SDK Asynchronously
(function(d, s, id) {
var js, fjs = d.getElementsByTagName(s)[0];
if (d.getElementById(id)) return;
js = d.createElement(s); js.id = id;
js.src = "//connect.facebook.net/en_US/all.js";
fjs.parentNode.insertBefore(js, fjs);
}(document, 'script', 'facebook-jssdk'));
</script>
Hope this works!
Anyway this is not the only problem i have. please check this post and help me if you can
impossible to read $_SESSION vars on PHP facebook app