check FB authorization (JS SDK) on server side - facebook

On client side i call FB.login and get response:
accessToken
expiresIn
signedRequest
userID
how i can check that is data is correct data, not fabricated ?

Related

Verify facebook token

I have a client application which authenticates with facebook and returns the token successfully. I would like to persist this data to the server without having to pass the entire object. Instead I would like to pass the resulting token from the client side authentication to my C# api in the authorization header and validate this token on the server.
Question, is it possible to verify the token on the server side? How to do it?
I am doing this via google, and need a facebook equivalent:
var googleResult = GoogleJsonWebSignature.ValidateAsync(
accessToken,
new GoogleJsonWebSignature.ValidationSettings
{
Audience = new[] { "secret key here.apps.googleusercontent.com" }
}
).GetAwaiter().GetResult();

Doubts about Security in Login for Web with Facebook Oauth JavaScript SDK that send ACCESS TOKEN to server

I have doubts about security of my process of authentication oauth with facebook..
I use login for web with javascript sdk with fb button:
I get an Access Token successfully and pass it to server(calling check_facebook_session.php) to make API call to Facebook Provider..
In the following code there is also the log in console of access token.
Everything works!!! on the server I use the php sdk to call the API REST with APPID, APPSECRET and ACCESS_TOKEN:
**
Now my question, have I a security problem?
Is a bad idea to pass the token to the server?
The token that is visible on the client can be used WITHOUT APP SECRET to get information about the user logged?
**
Note: Google+ Sign-In for server-side apps Implementing the one-time-code flow with step:
- Include the Google+ script on your page.
- Add the sign-in button to your page.
- Sign in the user.
- Send the authorization code to the server.
as explained in: https://developers.google.com/+/web/signin/server-side-flow
Unlike facebook google in the js client return a CODE, not an ACCES TOKEN and the server receive and use it to request ACCESS TOKEN.
Thanks..
Following is the javascript code for facebook:
window.fbAsyncInit = function() {
FB.init({
appId : FACEBOOK_APP_ID, // App ID
status : true, // check login status
cookie : false, // enable/disable cookies to allow the server to access the session
xfbml : true // parse XFBML
});
FB.Event.subscribe('auth.authResponseChange', function(response)
{
if (response.status === 'connected')
{
var accessToken = FB.getAuthResponse()['accessToken'];
console.log(accessToken);
$.ajax({
type: 'POST',
url: check_facebook_session.php,
contentType: 'application/x-www-form-urlencoded; charset=utf-8',
processData: false,
data: 'token=' + accessToken,
success: function(result)
{
if(result == 'SUCCESS'){window.location.href = fb_callback_url}
},
error: function(xhr)
{
alert('Request Status: ' + xhr.status + ' Status Text: ' + xhr.statusText + ' ' + xhr.responseText);
}
});
}
else if (response.status === 'not_authorized')
{
FB.login();
}
else
{
FB.login();
}
});
};
// Load the SDK asynchronously
.......
}(document));
I did some testing and came to the conclusions that I hope can be useful.
In Facebook SDK for JavaScript it automatically handles access token storage and tracking of login status, so apps using it do not need to create their own mechanisms for doing so, and can proceed to making API calls.
The system seems safe because I believe that the callback url of the call is the site that host the page and configured between those of the facebook application, so I can change the application id in the javascript code but the sdk response with error message and get the user's token pretending to be another application. This was already obvious to those who know the flow :-)
Passes the token to the server is definitely a bad idea because it can be snorted and used by simply calling https://graph.facebook.com/me?access_token=... to get user information, In the different flow of google the token is not passed but is passed the code necessary to obtain it.
The best solution to use advantage of client and server is it:
Used in conjunction with the Facebook SDK for JavaScript,
the PHP SDK can share user sessions seamlessly across the client and server.
If people are logged in with Facebook and have authorized your app,
the JavaScript SDK can pick up the user session and persist this in a cookie,
which the PHP SDK reads without any intervention on the developer's part.
To enable this functionality, ensure that when you embed and initialize the JS SDK,
you set both the status and the cookie parameters of the object passed to FB.init() to true.
Regards..
i think it is secure because the user's data is only returned with connected status after user authentication with facebook.
https://developers.facebook.com/docs/reference/javascript/FB.getLoginStatus/
I have followed Facebook example on getting access token by using $fb->getJavaScriptHelper();
https://developers.facebook.com/docs/php/howto/example_access_token_from_javascript
$helper = $fb->getJavaScriptHelper();
$accessToken = $helper->getAccessToken();
echo $accessToken->getValue();
P.S. Add try{} catch() {} blocks, as in Facebook example for error handling.

How to authenticate Facebook User after receiving response.status === 'connected'?

Perhaps I am going about this the wrong way but I have a website that allows facebook login.
If the user has already registered on my website
and is logged into facebook but not logged into my site
when visiting the login page i check for their facebook login status and get response.status === 'connected' via-
FB.Event.subscribe('auth.authResponseChange', function (response)
{
if (response.status === 'connected')
{
var s = JSON.stringify(response.authResponse);
LogMeIn(s, function(response)
{
HandleAjaxError(response, function(msg)
{
window.location = '/_/';
});
});
}
}
I then want to pass their authResponse object to the server and confirm that this userid works with this token before I log them in as this user
I have read to simply grab the json contents of -
https://graph.facebook.com/{userID}?access_token={accessToken}
and if it does not return an error then it is good! But when testing this method I noticed that the same access_token worked for two different user ids (meaning it did not return an error for the userid that was not logged in on my computer). Instead it returned the facebook user object with name , location etc.
This really surprised me, as I expected the access_token to work only with a single user id.
In an effort to prevent someone from simply changing the user id before continuing the script I need to authenticate via server side. What is a way to accomplish this?
Proof, go to these links to see profile information
My profile-
https://graph.facebook.com/1233822590?access_token=CAACCBJJZBgjABAOGmvmsou8gMYGulLHTgAr5ZCHZAU7pKEp0cMAeX8r4qHLpiVuZCOT1v0ulMZAxX5YfLJkcZBr9l6qJQoPxWS5Fs5ndohDnH6ZAPPfZCZCTQtwWgAZAg6I1PAOIpdtCc0OUaMmBZAvGiMm9gQhmNXRbocZD
Another userid with same access_token-
https://graph.facebook.com/100000116781159?access_token=CAACCBJJZBgjABAOGmvmsou8gMYGulLHTgAr5ZCHZAU7pKEp0cMAeX8r4qHLpiVuZCOT1v0ulMZAxX5YfLJkcZBr9l6qJQoPxWS5Fs5ndohDnH6ZAPPfZCZCTQtwWgAZAg6I1PAOIpdtCc0OUaMmBZAvGiMm9gQhmNXRbocZD
Nothing to be surprised. You can fetch the basic details of any user of the facebook using the access token of any user of the facebook.. So this isnt really good way to validate the token. Moreover, that confirmation of token part isnt required.
If you want the authorization through server side go through.this link

how to get USERID when user accept the request Facebook apprequests

i am using facebook apprequests to inviting friends as below
function invitefriends()
{
FB.init({
appId:'XXXXXXX', cookie:true,
status:true, xfbml:true
});
FB.ui({ method: 'apprequests',
message: 'Here is a new Requests dialog...'});
}
</script>
But how get friend id once he accept the request i am able to get below when user accept request
https://apps.facebook.com/XXXXXX/?request_ids=XXXXXXX&ref=notif&app_request_type=user_to_user&notif_t=app_request
from above i can get from userid but how to get userid who accept request
i tried to pass request_ids with redirect_uri but once user install application it get disappeared.
Looking at the Requests documentation, whenever a user uses your app to send a request, they are redirect post-send to your app with ?request=REQUEST_ID&to=ARRAY_OF_USER_IDS appended to the redirect_uri.
So, once you should setup your redirect URI to capture the request ID and the UID array and store it for later.
Then, when the user who received the request accepts it, they'll be directed to a URL similar to the following:
https://apps.facebook.com/APPNAME/?request_ids=REQUEST_ID&ref=notif&app_request_type=user_to_user&notif_t=app_request
You can then compare the request_id received here to the request ID you've already stored and then once the user has accepted and dropped onto your App, you'll receive a signed request which you can parse to retrieve their User ID.

Requests 2.0, empty data in graph after successfully sending requests

I'm seeing some strange behaviour with Requests.
I initiate a requests dialog with:
method: 'apprequests'
to: 'someUid'
(and some data for message, title, data)
The user approves the Request, and I get back a valid response, giving me the request Id, the user Ids it was sent to, and the updatedFrictionless flag. However, when reading the request from the graph later with either:
https://graph.facebook.com/?ids=REQUESTID_USERID&access_token=RECEIVINGUSERTOKEN
or
https://graph.facebook.com/REQUESTID_USERID?access_token=RECEIVINGUSERTOKEN
I get back no data !
The first graph call will give me an empty array (an un-named array not 'data', just simply [ ] )
The second, gives me 'false'
REQUESTID is the request Id I get back from the original call, USERID is the receiving USERID.
The receiving user is me, and I do see the request in my notifications, but using the graph explorer to check my 'apprequests', its empty.
Any ideas? I have Requests 2.0 enabled, and call FB.init with frictionlessRequests: true..
Does it work with your app access token?