Facebook Requires extended permission: publish_actions - facebook

I'm in the process of developing a Contest and Promotion-related Facebook app and my intent is to to create a tab on my company's page that will provide access to the app.
Once their, users can nominate local companies for awards. Later on; once the nominations are in, users can vote for a winner.
I've integrated Open Graph into my app so that I can take advantage of Object Types (Organization), Action Types (Nominate, Vote For), and Aggregations (Nominations). My main objective is to then transfer these actions onto the user's timeline.
I've used the recipebox example as my base. I've provided my code to demonstrate authentication and the post action required to submit an action type/object type combination.
<html xmlns="http://www.w3.org/1999/xhtml" dir="ltr" lang="en-US">
<head prefix="og: http://ogp.me/ns# og_<<app namespace>>: http://ogp.me/ns/apps/<<app namespace>>#">
<meta property="fb:app_id" content="<<app id>>" />
<meta property="og:type" content="<<app namespace>>:organization" />
<meta property="og:title" content="Client 1" />
<meta property="og:image" content="<<client image path>>" />
<meta property="og:description" content="Client 1 description here ... " />
<meta property="og:url" content="<<custom client URL>>">
<script src="http://connect.facebook.net/en_US/all.js"></script>
<script type="text/javascript">
// 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));
// Init the SDK upon load
window.fbAsyncInit = function() {
FB.init({
appId : '<<app id>>', // App ID
status : true, // check login status
cookie : true, // enable cookies to allow the server to access the session
xfbml : true // parse XFBML
});
// listen for and handle auth.statusChange events
FB.Event.subscribe('auth.statusChange', function(response) {
if (response.authResponse) {
// user has auth'd your app and is logged into Facebook
FB.api('/me', function(me){
if (me.name) {
document.getElementById('auth-displayname').innerHTML = me.name;
}
})
document.getElementById('auth-loggedout').style.display = 'none';
document.getElementById('auth-loggedin').style.display = 'block';
} else {
// user has not auth'd your app, or is not logged into Facebook
document.getElementById('auth-loggedout').style.display = 'block';
document.getElementById('auth-loggedin').style.display = 'none';
}
});
// respond to clicks on the login and logout links
document.getElementById('auth-loginlink').addEventListener('click', function(){
FB.login();
});
document.getElementById('auth-logoutlink').addEventListener('click', function(){
FB.logout();
});
}
function nominate () {
FB.api('/me/<<app namespace>>:Nominate&organization=<<custom client URL>>', 'post', function(response) {
if (! response || response.error) {
alert('Error occured');
console.log(response);
} else {
alert('Post was successful! Action ID: ' + response.id);
}
});
}
</script>
</head>
<body>
<div id="fb-root"></div>
<div id="auth-status">
<div id="auth-loggedout">
Login
</div>
<div id="auth-loggedin" style="display:none">
Hi, <span id="auth-displayname"></span>
(logout)
</div>
</div>
<h2>Client 1</h2>
<form>
<input type="button" value="Nominate" onclick="nominate()" />
</form>
<fb:activity actions="<<app namespace>>:nominate"></fb:activity>
</body>
</html>
A test user is encountering the following error:
Requires extended permission: publish_actions
And I am encountering the following error (I am an Admin for this app):
This method must be called with an app access_token
The first error is troubling to me. I cannot select publish_actions from Apps | <My App> | Permissions | Extended Permissions. Also, remedies I've encounted suggest I re-categorize my app to Games (this does not work) and to complete my Aggregations (I did; still does not work).
How can I overcome this error?
What can I do to fix my This method must be called with an app access_token error?
Thanks in advance,
Mike
EDIT
I believe the access_token error I was encountering was due to the fact that I was testing/interacting with the app directly on the Page Tab URL; not through Facebook.
I am no longer receiving the Requires extended permission: publish_actions error; however, my testers and developers are. I know that I am encountering this error because the publish_actions permission is not requested at the initial facebook.com login prompt.
If my Developers/Testers logout of Facebook, then log back in with my prompt:
FB.login(function (response) { }, { scope:'publish_actions'});
Then this permission and app is integrated into their Facebook session.
My final question is- is there a defacto, preferred method to request this permission without logging in/out of Facebook?

I have fixed both of my errors. Thank you to those who provided me with feedback and put me on the right path.
These errors have been resolved:
1. Requires extended permission: publish_actions
2. This method must be called with an app access_token
For starters, CBroe is right. Since I require extended permissions (publish_actions) I need to specify this is my options object after the callback function in FB.login() like so:
FB.login(function (response) {
if (response.authResponse) { // The user has authenticated
authenticatedSoDoSomething();
}
else { // The user has not authenticated
notAuthenticatedSoDoSomethingElse();
}
}, { scope:'publish_actions' });
Lastly, I had no success using the JavaScript SDK to publish an action to a user's timeline via FB.api(). This is the code I was using:
FB.api('/me/<<app namespace>>:<<my action>>&<<my object>>=<<a URL>>', 'post',
function(response) {
if (! response || response.error) {
alert('Error occured');
} else {
alert('Post was successful! Action ID: ' + response.id);
}
})
I neglected to include the app access token. The app access token can be constructed by concatenating the app id, followed by a pipe, followed by the app secret.
I used the PHP SDK to fulfill this request as I wanted to keep my api secret a secret. Here is [most] of the code I used:
require_once('facebook-php-sdk/src/facebook.php');
$facebook = new Facebook(
array(
'appId' => '<<my app id>>',
'secret' => '<<my app secret>>'));
$user = $facebook->getUser();
if ($user) {
try {
$user_profile = $facebook->api('/me');
}
catch (FacebookApiException $e) {
error_log($e);
$user = null;
echo json_encode(array('success' => false));
}
}
try {
$facebook->api('/' . $user . '/<<app namespace>>:<<my action>>&<<my object>>=<<a URL>>', 'POST', array('access_token' => $facebook->getAppId() . '|' . $facebook->getApiSecret()));
}
catch (FacebookApiException $e) {
echo var_dump($e->getResult());
}
Hope this helps!

For the second one, make the call with your App Access Token like the error says; if you're already doing this and it's failing, check the app isn't set to 'Native/Desktop' mode in the app's settings in the facebook App Dashboard. If it is, the app access token is untrusted and the API acts as though you didn't provide it.
For the first, are you sure users are granting publish_actions permission to your app? A call to /me/permissions with the user's access token will show you which permissions are granted. Note that the authenticated referrals / app center login flow is separate to your app's regular flow for users that end up there other than via an authenticated referral or the app center, so check you're including publish_actions in the scope in your call to the Oauth Dialog.

Related

How can I give the Facebook App access to the Facebook Page via the API?

As we all know, inside the Facebook for Developers interface, you can add Facebook Pages to a Facebook App as in the picture below and generate the Page Access Token.
I'm trying to do this programmatically via the API requests. Unfortunately, I did not find in the documentation of the request how to do this.
What have I done so far?
I can get the User ID and User Access Token via Facebook Login (Documentation).
I can get the list of Facebook Pages that a person owns. In the response, I have the Page ID and the Page Access Token (Documentation).
I have the Facebook app that is in development mode. That app has App ID and App Secret. With these values, I can get the App Access Token (Documentation).
I can set Webhook to the Facebook App with App ID and App Access Token (Documentation).
I can set the Webhook Subscriptions Fields for my Facebook App (Documentation).
Question: What kind of API request should I use to add a Facebook Page to the Facebook App?
The list of my requests:
I take Page ID and Page Access Token with this GET request cause this request returns the list of Facebook Pages that a person owns:
https://graph.facebook.com/v9.0/{user-id}/accounts?access_token={user-access-token}
I set the Webhook in my Facebook App with this POST request:
https://graph.facebook.com/v9.0/{app-id}/subscriptions?access_token={app-access-token}&callback_url={url-address}&verify_token={verify-token}&object=page&include_values=true
It successfully works and I see this Webhook in the "Webhooks" block of the Dashboard interface.
Then I make this POST request to set Webhook Subscriptions Fields:
https://graph.facebook.com/{page-id}/subscribed_apps?subscribed_fields=messages,messaging_postbacks,messaging_optins,message_deliveries,message_reads,messaging_payments,messaging_pre_checkouts,messaging_checkout_updates,messaging_account_linking,messaging_referrals,message_echoes,messaging_game_plays,standby,messaging_handovers,messaging_policy_enforcement,message_reactions,inbox_labels&access_token={page-access-token}
In this request, I use Page ID and Page Access Token from the first step.
Unfortunately, I have such an error message:
To subscribe to the messages field, one of these permissions is
needed: pages_messaging
I've been following down a similar rabbit hole. Indeed, Facebook documentation is confusing, but it ended up being pretty simple. Here is the modified Facebook Login example, which gets page access token and then adds necessary webhook subscriptions for page messaging. After you've run it, you will see the page is added to the App settings with the requested webhook subscriptions. Hope it helps šŸ¤“
<!DOCTYPE html>
<html>
<head>
<title>Facebook Login JavaScript Example</title>
<meta charset="UTF-8" />
</head>
<body>
<script>
let page_access_token = null
let page_id = null
function statusChangeCallback(response) {
// Called with the results from FB.getLoginStatus().
console.log('statusChangeCallback')
console.log(response) // The current login status of the person.
if (response.status === 'connected') {
// Logged into your webpage and Facebook.
testAPI()
} else {
// Not logged into your webpage or we are unable to tell.
document.getElementById('status').innerHTML =
'Please log ' + 'into this webpage.'
}
}
function checkLoginState() {
// Called when a person is finished with the Login Button.
FB.getLoginStatus(function (response) {
// See the onlogin handler
statusChangeCallback(response)
})
}
window.fbAsyncInit = function () {
FB.init({
appId: 'YOUR_APP_ID',
cookie: true, // Enable cookies to allow the server to access the session.
xfbml: true, // Parse social plugins on this webpage.
version: 'v12.0', // Use this Graph API version for this call.
})
FB.getLoginStatus(function (response) {
// Called after the JS SDK has been initialized.
statusChangeCallback(response) // Returns the login status.
})
}
// add webhooks to page subscriptions
function addPageSubscriptions() {
FB.api(
`/${page_id}/subscribed_apps`,
'POST',
{
subscribed_fields: [
'messages',
// any other webhook event: https://developers.facebook.com/docs/messenger-platform/webhook/#events
],
access_token: page_access_token,
},
function (response) {
if (response && !response.error) {
console.log({ response })
} else {
console.error(response.error)
}
},
)
}
// pages I have access to
function getPages() {
FB.api('/me/accounts', function (response) {
if (response && !response.error) {
console.log({ response })
page_access_token = response.data[0].access_token
page_id = response.data[0].id
addPageSubscriptions()
} else {
console.error(response.error)
}
})
}
function testAPI() {
// Testing Graph API after login. See statusChangeCallback() for when this call is made.
console.log('Welcome! Fetching your information.... ')
// Me
FB.api('/me', function (response) {
console.log('Successful login for: ' + response.name)
document.getElementById('status').innerHTML =
'Thanks for logging in, ' + response.name + '!'
getPages()
})
}
</script>
<!-- The JS SDK Login Button -->
<!-- IMPORTANT: Define the scopes for managing pages metadata and pages_messaging for the webhooks -->
<fb:login-button
scope="public_profile,email,pages_manage_metadata,pages_messaging"
onlogin="checkLoginState();"
>
</fb:login-button>
<div id="status"></div>
<!-- Load the JS SDK asynchronously -->
<script
async
defer
crossorigin="anonymous"
src="https://connect.facebook.net/en_US/sdk.js"
></script>
</body>
</html>

Facebook login with JavaScript SDK error: "redirect URI not whitelisted" [duplicate]

This question already has answers here:
Javascript Parse Facebook Login Issue
(4 answers)
Closed 6 years ago.
I want my website to login with facebook but I am seeing this error.
Given URL is not whitelisted in Client OAuth Settings: This redirect failed because the redirect URI is not whitelisted in the appā€™s Client OAuth Settings. Make sure Client and Web OAuth Login are on and add all your app domains as Valid OAuth Redirect URIs.
<!DOCTYPE html>
<html>
<head>
<title>Facebook Login JavaScript Example</title>
<meta charset="UTF-8">
</head>
<body>
<script>
// This is called with the results from from FB.getLoginStatus().
function statusChangeCallback(response) {
console.log('statusChangeCallback');
console.log(response);
// The response object is returned with a status field that lets the
// app know the current login status of the person.
// Full docs on the response object can be found in the documentation
// for FB.getLoginStatus().
if (response.status === 'connected') {
// Logged into your app and Facebook.
testAPI();
} else if (response.status === 'not_authorized') {
// The person is logged into Facebook, but not your app.
document.getElementById('status').innerHTML = 'Please log ' +
'into this app.';
} else {
// The person is not logged into Facebook, so we're not sure if
// they are logged into this app or not.
document.getElementById('status').innerHTML = 'Please log ' +
'into Facebook.';
}
}
// This function is called when someone finishes with the Login
// Button. See the onlogin handler attached to it in the sample
// code below.
function checkLoginState() {
FB.getLoginStatus(function(response) {
statusChangeCallback(response);
});
}
window.fbAsyncInit = function() {
FB.init({
appId: 'XXXXXXXXXXXX',
cookie : true, // enable cookies to allow the server to access
// the session
xfbml : true, // parse social plugins on this page
version : 'v2.5' // use version 2.2
});
// Now that we've initialized the JavaScript SDK, we call
// FB.getLoginStatus(). This function gets the state of the
// person visiting this page and can return one of three states to
// the callback you provide. They can be:
//
// 1. Logged into your app ('connected')
// 2. Logged into Facebook, but not your app ('not_authorized')
// 3. Not logged into Facebook and can't tell if they are logged into
// your app or not.
//
// These three cases are handled in the callback function.
FB.getLoginStatus(function(response) {
statusChangeCallback(response);
});
};
// 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/sdk.js";
fjs.parentNode.insertBefore(js, fjs);
}(document, 'script', 'facebook-jssdk'));
// Here we run a very simple test of the Graph API after login is
// successful. See statusChangeCallback() for when this call is made.
function testAPI() {
console.log('Welcome! Fetching your information.... ');
FB.api('/me', function(response) {
console.log('Successful login for: ' + response.name);
document.getElementById('status').innerHTML =
'Thanks for logging in, ' + response.name + '!';
});
}
</script>
<!--
Below we include the Login Button social plugin. This button uses
the JavaScript SDK to present a graphical Login button that triggers
the FB.login() function when clicked.
-->
<fb:login-button scope="public_profile,email" onlogin="checkLoginState();">
</fb:login-button>
<div id="status">
</div>
</body>
</html>
You must make sure you have registered your app with the developer page
Go here
For the facebook login docs
Go here
Then when you register your app make sure whatever URL you are using as the redirect page is the same as your app is sending too.
For example
http://example.com
is not,
http://www.example.com
To settup url as the local host refer to
this post
Please make sure you are setting your
$app_id = "xxx";
$app_secret = "xxx";
$my_url ="http://localhost:3080/example.php";
All to the correct data as specified inside your app settings when you create your app on facebook's developer page.
To make this as clear as possible.
Go to your app page and enter the url of the page in your localhost.
Then go to your code and add the exact same url.
in app settings,
http://localhost
in your code
http://localhost
If there is a port number after your localhost,
in app settings,
http://localhost:8080
in your code
http://localhost:8080
If there is a file after your localhost
in app settings,
http://localhost/myfile.php
in your code
http://localhost/myfile.php
Please try this code. replace your code with this code and do not forget to change the
YOUR_FACBEOOK_APP_ID
to your own.
<div id="fb-root"></div>
<script>
window.fbAsyncInit = function() {
FB.init({
appId: 'xxxxxxxxxxxxx',
status: true,
cookie: true,
xfbml: true
});
};
// 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));
function login() {
FB.login(function(response) {
// handle the response
console.log("Response goes here!");
}, {scope: 'read_stream,publish_stream,publish_actions,read_friendlists'});
}
function logout() {
FB.logout(function(response) {
// user is now logged out
});
}
var status = FB.getLoginStatus();
console.log(status);
</script>
<button onclick="javascript:login();">Login Facebook</button>
<br>
<button onclick="javascript:logout();">Logout from Facebook</button>
In my case, modifying the /etc/hosts file to map '127.0.0.1' to something like myapp.com - so that your application has a ā€œrealā€ URL, resolved the issue.
Same is to be added to "Valid OAuth redirect URIs" in the Client OAuth Settings.
I has the same problem .
For me the solution was to add both WWW and no-WWW versions of my site to whitelist in Client OAuth Settings.

Get session after log in with JavaScript SDK on serverside and get the username also

I am trying to do my first Facebook log in. So I am using the Facebook SDK for JavaScript for implementing the pop up log in and then i want to use the SDK for PHP to store the username in the database ( for displaying in my web app ).
The problem is that this PHP code i am using doesn't get the session after log in by JavaScript pop up and first refresh. It get`s the info after a second refresh.
The second problem is that i cant find a way to get the username from the id.
Username is facebook.com/john.doe1 and is equivalent with the id facebook.com/1241245235 .
So right now i am using the Facebook Login for the Web with the JavaScript SDK which is the standard log in with JavaScript.
<!DOCTYPE html>
<html>
<head>
<title>Facebook Login JavaScript Example</title>
<meta charset="UTF-8">
</head>
<body>
<script>
// This is called with the results from from FB.getLoginStatus().
function statusChangeCallback(response) {
console.log('statusChangeCallback');
console.log(response);
// The response object is returned with a status field that lets the
// app know the current login status of the person.
// Full docs on the response object can be found in the documentation
// for FB.getLoginStatus().
if (response.status === 'connected') {
// Logged into your app and Facebook.
testAPI();
} else if (response.status === 'not_authorized') {
// The person is logged into Facebook, but not your app.
document.getElementById('status').innerHTML = 'Please log ' +
'into this app.';
} else {
// The person is not logged into Facebook, so we're not sure if
// they are logged into this app or not.
document.getElementById('status').innerHTML = 'Please log ' +
'into Facebook.';
}
}
// This function is called when someone finishes with the Login
// Button. See the onlogin handler attached to it in the sample
// code below.
function checkLoginState() {
FB.getLoginStatus(function(response) {
statusChangeCallback(response);
});
}
window.fbAsyncInit = function() {
FB.init({
appId : '{your-app-id}',
cookie : true, // enable cookies to allow the server to access
// the session
xfbml : true, // parse social plugins on this page
version : 'v2.1' // use version 2.1
});
// Now that we've initialized the JavaScript SDK, we call
// FB.getLoginStatus(). This function gets the state of the
// person visiting this page and can return one of three states to
// the callback you provide. They can be:
//
// 1. Logged into your app ('connected')
// 2. Logged into Facebook, but not your app ('not_authorized')
// 3. Not logged into Facebook and can't tell if they are logged into
// your app or not.
//
// These three cases are handled in the callback function.
FB.getLoginStatus(function(response) {
statusChangeCallback(response);
});
};
// 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/sdk.js";
fjs.parentNode.insertBefore(js, fjs);
}(document, 'script', 'facebook-jssdk'));
// Here we run a very simple test of the Graph API after login is
// successful. See statusChangeCallback() for when this call is made.
function testAPI() {
console.log('Welcome! Fetching your information.... ');
FB.api('/me', function(response) {
console.log('Successful login for: ' + response.name);
document.getElementById('status').innerHTML =
'Thanks for logging in, ' + response.name + '!';
});
}
</script>
<!--
Below we include the Login Button social plugin. This button uses
the JavaScript SDK to present a graphical Login button that triggers
the FB.login() function when clicked.
-->
<fb:login-button scope="public_profile,email" onlogin="checkLoginState();">
</fb:login-button>
<div id="status">
</div>
</body>
</html>
After I log in I want to pass the information to server side (PHP) so i am using this code:
require_once 'lib/fb/autoload.php';
use Facebook\FacebookSession;
use Facebook\FacebookRequest;
use Facebook\GraphUser;
use Facebook\FacebookRequestException;
use Facebook\FacebookJavaScriptLoginHelper;
FacebookSession::setDefaultApplication('xxxxx','xxxxx');
$helper = new FacebookJavaScriptLoginHelper();
try {
$session = $helper->getSession();
} catch(FacebookRequestException $ex) {
// When Facebook returns an error
} catch(\Exception $ex) {
// When validation fails or other local issues
}
if($session) {
try {
$user_profile = (new FacebookRequest(
$session, 'GET', '/me'
))->execute()->getGraphObject(GraphUser::className());
echo "Name: " . $user_profile->getName();
echo '<br>';
echo "Id: " . $user_profile->getId();
echo '<br>';
echo "Link: " . $user_profile->getLink();
} catch(FacebookRequestException $e) {
echo "Exception occured, code: " . $e->getCode();
echo " with message: " . $e->getMessage();
}
}
The username field has been deprecated with Graph API v2.0. Have a look at
https://developers.facebook.com/docs/apps/changelog#v2_0_graph_api
/me/username is no longer available.
Why you switch from frontend to backend is also not really clear to me. I'd recommend that you decide whether you want to use PHP or JavaScript. But nevertheless, you'll not be able to get the username anymore.

Facebook friend list fetching

I have googled and looked at other similar questions posted on Stackoverflow but none of them seem to work. I need to be able to login using the FB login on my website and then retrieve my friend list. I used the code from FB developer's site and I can login but nothing else executes. In particular I would like to understand two things:
How can I modify this code to turn the login into a logout button once I am logged in?
How can I get the testAPI() function to execute?
Here is my entire code: the login works but I see no output in my JS console.
<html>
<title> Test Title</title>
<body>
<h1> About Test Title </h1>
<p>Random text.</p>
<div id="fb-root"></div>
<script>
window.fbAsyncInit = function() {
FB.init({
appId : '345435435435', // valid App ID is used here
channelUrl : '//www.my website.com/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
});
// Here we subscribe to the auth.authResponseChange JavaScript event. This event is fired
// for any authentication related change, such as login, logout or session refresh. This means that
// whenever someone who was previously logged out tries to log in again, the correct case below
// will be handled.
FB.Event.subscribe('auth.authResponseChange', function(response) {
// Here we specify what we do with the response anytime this event occurs.
if (response.status === 'connected') {
// The response object is returned with a status field that lets the app know the current
// login status of the person. In this case, we're handling the situation where they
// have logged in to the app.
console.log('Connected caseā€¦ ');
testAPI();
} else if (response.status === 'not_authorized') {
// In this case, the person is logged into Facebook, but not into the app, so we call
// FB.login() to prompt them to do so.
// In real-life usage, you wouldn't want to immediately prompt someone to login
// like this, for two reasons:
// (1) JavaScript created popup windows are blocked by most browsers unless they
// result from direct interaction from people using the app (such as a mouse click)
// (2) it is a bad experience to be continually prompted to login upon page load.
FB.login();
console.log('Not authorized caseā€¦ ');
} else {
// In this case, the person is not logged into Facebook, so we call the login()
// function to prompt them to do so. Note that at this stage there is no indication
// of whether they are logged into the app. If they aren't then they'll see the Login
// dialog right after they log in to Facebook.
// The same caveats as above apply to the FB.login() call here.
FB.login();
console.log('else caseā€¦ ');
}
});
};
// 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));
// Here we run a very simple test of the Graph API after login is successful.
// This testAPI() function is only called in those cases.
function testAPI() {
console.log('Welcome! Fetching your information.... ');
FB.api('/me', function(response) {
console.log('Good to see you, ' + response.name + '.');
});
}
</script>
<!--
Below we include the Login Button social plugin. This button uses the JavaScript SDK to
present a graphical Login button that triggers the FB.login() function when clicked.
Learn more about options for the login button plugin:
/docs/reference/plugins/login/ -->
<fb:login-button autologoutlink="true" show-faces="true" width="200" max-rows="1"></fb:login-button>
</body>
</html>
oFor the logout, you can use
FB.logout(function(response) {
//console.log(response);
// do something usefull ...
});
and put that on a button. BUT: you are currently logging off the user from Facebook AND from your app, users might find that strange?
Logout on a button as requested:
<a href='#' onClick='doLogout();'>Logout from Facebook</a>
...
function doLogout() {
FB.logout(function(response) {
//console.log(response);
alert("Bye bye...");
});
}

Open Graph error on submission - publishing a stream story

Can you spot my error?
I'm really struggling to get an open graph action approved. I want people to Share (Action) a Photo (Object) and have requested the user message and explicitly shared functions. The latest comment I have had back from Facebook is this:
We are unable to test this action due to an error within your app.
Please make sure that your action functions correctly by testing with
the Auth Dialog Preview User and re-submit.
Not very helpful!
I have tested my action with the Auth Dialog Preview User and it worked fine. I have also tested my page with the object debugger which returned the response code 200 - which apparently means all is fine (is that correct?).
Below is the code I am using on my test page and was hoping someone would be able to point out where my errors are as I can't see it:
<head>
meta tags here
<script type="text/javascript">
function Share()
{
FB.api(
'/me/NAMESPACE:share&photo=TEST PAGE URL&message=Cool photos&fb:explicitly_shared=true&access_token=ACCESS TOKEN','POST', function(response) {
if (!response || response.error) {
alert('Error occured');
} else {
alert('Post was successful! Action ID: ' + response.id);
}
});
}
</script>
<script type="text/javascript">
window.fbAsyncInit = function() {
FB.Canvas.setAutoGrow();
}
// Do things that will sometimes call sizeChangeCallback()
function sizeChangeCallback() {
FB.Canvas.setSize({ width: 810, height: 1180 });
}
</script>
</head>
<body>
<div id="fb-root"></div>
<script>
// 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));
// Init the SDK upon load
window.fbAsyncInit = function() {
FB.init({
appId : 'APP ID', // App ID
channelUrl : '//CHANNEL FILE URL', // Path to your Channel File
status : true, // check login status
cookie : true, // enable cookies to allow the server to access the session
xfbml : true, // parse XFBML
oauth :true
});
// listen for and handle auth.statusChange events
FB.Event.subscribe('auth.statusChange', function(response) {
if (response.authResponse) {
// user has auth'd your app and is logged into Facebook
FB.api('/me', function(me){
if (me.name) {
document.getElementById('auth-displayname').innerHTML = me.name;
}
})
document.getElementById('auth-loggedout').style.display = 'none';
document.getElementById('auth-loggedin').style.display = 'block';
} else {
// user has not auth'd your app, or is not logged into Facebook
document.getElementById('auth-loggedout').style.display = 'block';
document.getElementById('auth-loggedin').style.display = 'none';
}
});
// respond to clicks on the login and logout links
document.getElementById('auth-loginlink').addEventListener('click', function(){
FB.login();
});
document.getElementById('auth-logoutlink').addEventListener('click', function(){
FB.logout();
});
}
function loginUser() {
FB.login(function(response) { }, {scope:'publish_actions, email'});
}
</script>
<div id="auth-status">
<div id="auth-loggedout">
<img src="login_btn.png">
</div>
<div id="auth-loggedin" style="display:none">
</div>
</div>
<form>
<input class="shr-btn" type="button" value="" onClick="Share()" />
</form>
</body>
Any help would be gratefully received.
Many thanks
D
Aaarrggh. I've now had this response from Facebook:
Your code is currently configured to publish a stream story. You must
change your code so that when the test user triggers the action it
produces an open graph story. Please make the appropriate changes and
resubmit.
Can someone please let me know what I am doing wrong? I thought the code was set up to publish an open graph story - but apparently now.
If someone could point out what I am doing wrong I would be eternally grateful.
Many thanks.
D
This seems to have more to do with how you're passing in the additional parameters in this line:
'/me/NAMESPACE:share&photo=TEST PAGE URL&message=Cool photos&
fb:explicitly_shared=true&access_token=ACCESS TOKEN','POST', function(response)
You really want to do something more like:
FB.api('/me/NAMESPACE:share', 'post',
{ photo : 'TEST_PAGEURL', message : 'Cool photos' }, function(response));
The important thing here is to include your custom JSON content as the third parameter to the function. It seems like the URL parameters method might be triggering that sort of message, since it's an older implementation.
No, it is not because you are creating a story using the verb "share." I just got a story approved by Facebook where I used the verb "share." And my story was rejected earlier for the same reason as yours.
Basically you cannot post something to an album or any other kind of post when you are using an open graph story. For example the following is not allowed:
$data = $facebook->api('/me/photos', 'post', $args);//disallowed
$facebook->api(
'me/invig-test:share',
'POST',
array(
'app_id' => $configParam['appId'],
'type' => "test:photo",
'photo' => "http://samples.ogp.me/574859819237737",
'title' => "a photo",
'image[0][url]'=>"http://www.testapp.com/".$imgFile,
'image[0][user_generated]'=>'true',
'message' => $comments,
'fb:explicitly_shared'=>true,
)
);
Instead only do the "share":
$facebook->api(
'me/invig-test:share',
'POST',
array(
'app_id' => $configParam['appId'],
'type' => "test:photo",
'photo' => "http://samples.ogp.me/574859819237737",
'title' => "a photo",
'image[0][url]'=>"http://www.testapp.com/".$imgFile,
'image[0][user_generated]'=>'true',
'message' => $comments,
'fb:explicitly_shared'=>true,
)
);