I am developing an app where it retrieves the current user facebook friends. My Code is working on my device but when I run it on any other devices, its not displaying any results.
Could you please let me know where I am going wrong.
my code is as follows :
public class FaceBook extends Activity implements SearchView.OnQueryTextListener, SearchView.OnCloseListener{
ArrayList<Param> facebook_names = new ArrayList<Param>();
Param name = null;
Names_Adapter adapter;
ListView Names_List;
SearchView searchView;
int check_search =1;
ArrayList<Param>new_names;
private UiLifecycleHelper uiHelper;
private static final int REAUTH_ACTIVITY_CODE = 100;
#SuppressLint("NewApi")
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_face_book);
ActionBar bar = getActionBar();
bar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM);
bar.setCustomView(R.layout.custom_titlebar);
bar.setBackgroundDrawable(getResources().getDrawable(R.drawable.header));
//bar.setTitle("Main Menu");
bar.setDisplayShowHomeEnabled(true);
bar.setHomeButtonEnabled(true);
uiHelper = new UiLifecycleHelper(this, callback);
uiHelper.onCreate(savedInstanceState);
TextView myTitleText = (TextView) findViewById(R.id.mytext);
if ( myTitleText != null ) {
myTitleText.setText("Facebook");
}
Log.d("COMP", "TEST");
Names_List = (ListView) findViewById(R.id.listView1);
ImageButton reload = (ImageButton) findViewById(R.id.reload);
reload.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent restart = new Intent(FaceBook.this, FaceBook.class);
startActivity(restart);
finish();
}
});
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REAUTH_ACTIVITY_CODE) {
uiHelper.onActivityResult(requestCode, resultCode, data);
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.face_book, menu);
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
searchView = (SearchView) findViewById(R.id.searchView1);
searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
searchView.setIconifiedByDefault(false); // Do not iconify the widget; expand it by default
return true;
}
#Override
public boolean onQueryTextSubmit(String arg0) {
// TODO Auto-generated method stub
return false;
}
#Override
public boolean onQueryTextChange(String query) {
// TODO Auto-generated method stub
if(!query.isEmpty())
{
check_search = 0;
new_names = new ArrayList<Param>();
for(int i=0;i<facebook_names.size();i++)
{
if(facebook_names.get(i).getName().toLowerCase().startsWith(query))
{
Param new_param = new Param(facebook_names.get(i).getUrl(),facebook_names.get(i).getName(),facebook_names.get(i).getPic());
new_names.add(new_param);
adapter.notifyDataSetChanged();
}
}
Names_Adapter adapter = new Names_Adapter(FaceBook.this,R.layout.facebook_names_list,new_names);
Names_List.setAdapter(adapter);
adapter.notifyDataSetChanged();
}
else
{
check_search=1;
adapter = new Names_Adapter(FaceBook.this,R.layout.facebook_names_list,facebook_names);
Names_List.setAdapter(adapter);
}
return false;
}
#Override
public boolean onClose() {
// TODO Auto-generated method stub
Names_List.setAdapter(adapter);
return false;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// TODO Auto-generated method stub
int itemId = item.getItemId();
switch (itemId) {
case android.R.id.home:
FaceBook.this.finish();
break;
}
return super.onOptionsItemSelected(item);
}
private void makeRequest(Session session)
{
String fqlQuery = "SELECT uid,name,pic,profile_url FROM user WHERE uid IN " +
"(SELECT uid2 FROM friend WHERE uid1 = me()) ORDER BY first_name";
Bundle params = new Bundle();
params.putString("q", fqlQuery);
session = Session.getActiveSession();
Request request = new Request(session,
"/fql",
params,
HttpMethod.GET,
new Request.Callback(){
public void onCompleted(Response response) {
Log.i("TAG", "Result: " + response.toString());
try{
GraphObject graphObject = response.getGraphObject();
JSONObject jsonObject = graphObject.getInnerJSONObject();
Log.d("data", jsonObject.toString(0));
JSONArray array = jsonObject.getJSONArray("data");
for(int i=0;i<array.length();i++){
JSONObject friend = array.getJSONObject(i);
name = new Param(friend.optString("profile_url"),friend.optString("name"),friend.optString("pic"));
facebook_names.add(name);
// Log.d("uid",friend.getString("uid"));
// Log.d("name", friend.getString("name"));
//Log.d("pic_square",friend.getString("pic_square"));
adapter = new Names_Adapter(FaceBook.this,R.layout.facebook_names_list,facebook_names);
Names_List.setAdapter(adapter);
searchView.setOnQueryTextListener(FaceBook.this);
searchView.setOnCloseListener(FaceBook.this);
Names_List.setOnItemClickListener(new OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,
long arg3) {
// TODO Auto-generated method stub
Intent intent = new Intent(FaceBook.this,Web_Activity.class);
if(check_search==0)
{
intent.putExtra("WEB",new_names.get(arg2).getUrl());
intent.putExtra("NAME",new_names.get(arg2).getName());
}
else
{
intent.putExtra("WEB",facebook_names.get(arg2).getUrl());
intent.putExtra("NAME",facebook_names.get(arg2).getName());
}
startActivity(intent);
}
});
}
}catch(JSONException e){
e.printStackTrace();
}
}
});
Request.executeBatchAsync(request);
}
private void onSessionStateChange(final Session session, SessionState state, Exception exception) {
if (session != null && session.isOpened()) {
// Get the user's data.
makeRequest(session);
}
}
public void onResume() {
super.onResume();
Session session = Session.getActiveSession();
if (session != null &&
(session.isOpened() || session.isClosed()) ) {
onSessionStateChange(session, session.getState(), null);
}
uiHelper.onResume();
}
private Session.StatusCallback callback = new Session.StatusCallback() {
#Override
public void call(final Session session, final SessionState state, final Exception exception) {
onSessionStateChange(session, state, exception);
}
};
#Override
public void onSaveInstanceState(Bundle bundle) {
super.onSaveInstanceState(bundle);
uiHelper.onSaveInstanceState(bundle);
}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
}
#Override
public void onDestroy() {
super.onDestroy();
uiHelper.onDestroy();
}
}
I also tried using restFB to access the user Facebook friends.
AccessToken accessToken = new DefaultFacebookClient().obtainAppAccessToken(appid,app secret;
FacebookClient facebookClient = new DefaultFacebookClient(accessToken.getAccessToken());
User user = facebookClient.fetchObject("me", User.class);
When I do this, it gives me an error stating that a valid access token must be used to retrieve user values.
Go to the Facebook Developer site, and under the 'Status and Review' for your app, make it PUBLIC. You can always remove from Public later after your 'temporary' testing is complete.
or
Another way would be to print out the key hashes from each device that you are testing your app on, and add these as key hashes into Settings>Android in the FB developer for your app.
Related
i have implement social auth for integration of facebook now i want to get user profile info and unique id .I have get access token but unable to get user profile info .I have implement it by following
public class SignUp extends Activity implements OnClickListener {
private EditText email_mEditText, password_mEditText;
SocialAuthAdapter socialAuthAdapter;
private RelativeLayout facebook_layout, twitter_layout, googleplus_layout, linkdin_layout;
private Button signIn_mButton;
String email_mString, password_mString;
private ImageView backIcon_mImageView, logoIcon_mImageView;
private TextView forgotpassword_mTextView;
String emailid_mString ;
EditText emailid_mEt;
Button submit_mbtn;
Dialog dialog;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.sign_up);
signIn_mButton = (Button) findViewById(R.id.signin_button);
email_mEditText = (EditText) findViewById(R.id.email_editText);
password_mEditText = (EditText) findViewById(R.id.password_editText);
backIcon_mImageView = (ImageView) findViewById(R.id.backicon_imageView);
logoIcon_mImageView = (ImageView) findViewById(R.id.logoicon_imageView);
facebook_layout = (RelativeLayout) findViewById(R.id.facebook_layout);
twitter_layout = (RelativeLayout) findViewById(R.id.twitter_layout);
googleplus_layout = (RelativeLayout) findViewById(R.id.google_layout);
linkdin_layout = (RelativeLayout) findViewById(R.id.linkdin_layout);
facebook_layout.setOnClickListener(this);
twitter_layout.setOnClickListener(this);
googleplus_layout.setOnClickListener(this);
linkdin_layout.setOnClickListener(this);
socialAuthAdapter = new SocialAuthAdapter(new ResponseListener());
signIn_mButton.setOnClickListener(this);
backIcon_mImageView.setOnClickListener(this);
logoIcon_mImageView.setOnClickListener(this);
forgotpassword_mTextView = (TextView) findViewById(R.id.forgotpassword_textView);
forgotpassword_mTextView.setPaintFlags(forgotpassword_mTextView.getPaintFlags() | Paint.UNDERLINE_TEXT_FLAG);
forgotpassword_mTextView.setOnClickListener(this);
}
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.signin_button:
email_mString = email_mEditText.getText().toString();
password_mString = password_mEditText.getText().toString();
if ((email_mString.isEmpty()) && (password_mString.isEmpty())) {
email_mEditText.addTextChangedListener(new TextWatcher() {
#Override
public void afterTextChanged(Editable s) {
}
#Override
public void beforeTextChanged(CharSequence arg0, int arg1, int arg2, int arg3) {
// TODO Auto-generated method stub
email_mEditText.setError("Value required");
}
#Override
public void onTextChanged(CharSequence arg0, int arg1, int arg2, int arg3) {
// TODO Auto-generated method stub
email_mEditText.setError(null);
}
});
} else if ((email_mString.isEmpty())) {
email_mEditText.setError("Please Enter the Email ");
} else if ((password_mString.isEmpty())) {
password_mEditText.setError("Please Enter the Password ");
} else {
Log.d("u r", "ur in else part");
new Thread(null, threadEventListing, "").start();
}
break;
case R.id.backicon_imageView:
Intent signInIntent = new Intent(SignUp.this, SignIn.class);
startActivity(signInIntent);
overridePendingTransition(R.anim.slide_in_left, R.anim.slide_out_left);
finish();
break;
case R.id.logoicon_imageView:
Intent signIntent = new Intent(SignUp.this, SignIn.class);
startActivity(signIntent);
overridePendingTransition(R.anim.slide_in_left, R.anim.slide_out_left);
finish();
break;
case R.id.forgotpassword_textView:
Log.d("hello", "u clicked FOrgot textview");
dialog = new Dialog(this);
dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
dialog.setContentView(R.layout.forgot_password);
emailid_mEt=(EditText)dialog.findViewById(R.id.etforgotpassword);
submit_mbtn=(Button)dialog.findViewById(R.id.btnsubmit);
submit_mbtn.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
emailid_mString = emailid_mEt.getText().toString();
new Thread(null,threadForgotPassword,"").start();
}
});
dialog.show();
break;
case R.id.facebook_layout:
socialAuthAdapter.authorize(SignUp.this, Provider.FACEBOOK);
socialAuthAdapter.signOut(this, Provider.FACEBOOK.toString());
break;
case R.id.twitter_layout:
socialAuthAdapter.authorize(SignUp.this, Provider.TWITTER);
socialAuthAdapter.signOut(this, Provider.TWITTER.toString());
break;
case R.id.google_layout:
socialAuthAdapter.authorize(SignUp.this, Provider.GOOGLEPLUS);
socialAuthAdapter.signOut(this, Provider.GOOGLEPLUS.toString());
break;
case R.id.linkdin_layout:
socialAuthAdapter.authorize(SignUp.this, Provider.LINKEDIN);
socialAuthAdapter.signOut(this, Provider.LINKEDIN.toString());
break;
}
}
#Override
public void onBackPressed() {
// TODO Auto-generated method stub
Intent signInIntent = new Intent(SignUp.this, SignIn.class);
startActivity(signInIntent);
overridePendingTransition(R.anim.slide_in_left, R.anim.slide_out_left);
finish();
}
private final class ResponseListener implements DialogListener {
public void onComplete(Bundle values) {
Log.d("tag", "In on comppleter");
String token = socialAuthAdapter.getCurrentProvider().getAccessGrant().getKey();
Log.d("Token", token);
}
#Override
public void onBack() {
// TODO Auto-generated method stub
}
#Override
public void onCancel() {
// TODO Auto-generated method stub
}
#Override
public void onError(SocialAuthError arg0) {
// TODO Auto-generated method stub
}
}
}
Use this Code
public class MainFragment extends Fragment {
private static final String TAG = "MainFragment";
private UiLifecycleHelper uiHelper;
private Session.StatusCallback callback = new Session.StatusCallback() {
#Override
public void call(Session session, SessionState state, Exception exception) {
onSessionStateChange(session, state, exception);
}
};
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
uiHelper = new UiLifecycleHelper(getActivity(), callback);
uiHelper.onCreate(savedInstanceState);
View view = inflater.inflate(R.layout.main, container, false);
LoginButton authButton = (LoginButton) view.findViewById(R.id.authButton);
authButton.setReadPermissions(Arrays.asList("public_profile", "email", "user_location"));
authButton.setFragment(this);
return view;
}
private void onSessionStateChange(Session session, SessionState state, Exception exception) {
if (state.isOpened()) {
Log.i(TAG, "Logged in...");
makeMeRequest(session);
} else if (state.isClosed()) {
Log.i(TAG, "Logged out...");
}
}
private void makeMeRequest(final Session session) {
// Make an API call to get user data and define a
// new callback to handle the response.
Request request = Request.newMeRequest(session, new Request.GraphUserCallback() {
/*
* #Override public void onCompleted(GraphUser user, Response
* response) { // If the response is successful if (session ==
* Session.getActiveSession()) { if (user != null) { // Set the
* id for the ProfilePictureView // view that in turn displays
* the profile picture. Log.e("user",user.toString()); } } if
* (response.getError() != null) { // Handle errors, will do so
* later. } }
*/
#Override
public void onCompleted(GraphUser user, Response response) {
// TODO Auto-generated method stub
Log.e("FB Return", user.toString());
Log.e("FullName", user.getName());
Log.e("Id", user.getId());
Log.e("username", "" + user.getUsername());
Log.e("Fname", user.getFirstName());
Log.e("Fname", user.getLastName());
Log.e("gender", user.asMap().get("gender").toString());
String gender = user.asMap().get("gender").toString();
String email = (String) user.asMap().get("email") + "";
Log.e("email", email);
}
});
request.executeAsync();
}
#Override
public void onResume() {
super.onResume();
// For scenarios where the main activity is launched and user
// session is not null, the session state change notification
// may not be triggered. Trigger it if it's open/closed.
Session session = Session.getActiveSession();
if (session != null && (session.isOpened() || session.isClosed())) {
onSessionStateChange(session, session.getState(), null);
}
uiHelper.onResume();
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
uiHelper.onActivityResult(requestCode, resultCode, data);
}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
}
#Override
public void onDestroy() {
super.onDestroy();
uiHelper.onDestroy();
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
uiHelper.onSaveInstanceState(outState);
}
}
Since you are using Social Auth, so you can try this :
private final class ProfileDataListener implements SocialAuthListener {
#Override
public void onExecute(Profile t) {
Log.d("Custom-UI", "Receiving Data");
Profile profileMap = t;
Log.d("Custom-UI", "Validate ID = " + profileMap.getValidatedId());
Log.d("Custom-UI", "First Name = " + profileMap.getFirstName());
Log.d("Custom-UI", "Last Name = " + profileMap.getLastName());
Log.d("Custom-UI", "Email = " + profileMap.getEmail());
Log.d("Custom-UI", "Gender = " + profileMap.getGender());
Log.d("Custom-UI", "Country = " + profileMap.getCountry());
Log.d("Custom-UI", "Language = " + profileMap.getLanguage());
Log.d("Custom-UI", "Location = " + profileMap.getLocation());
Log.d("Custom-UI", "Profile Image URL = " + profileMap.getProfileImageURL()); }
I hope anybody can help me ! I want to change my code for the new facebook sdk 4.0 but there is only a little description and i´m getting crazy and don´t know how to make the new code with facebook login button and accesstoken
target of this code is that the user logs in with his facebook account and checks if the user already exits. if not then insert new user with email and facebook id and name
I have marked the codes with //needs to be changed and //needs to be changed END
Thanx in advance for any help !!!
import com.facebook.AccessToken;
import com.facebook.CallbackManager;
import com.facebook.FacebookCallback;
import com.facebook.FacebookException;
import com.facebook.FacebookSdk;
import com.facebook.login.LoginResult;
import com.facebook.login.widget.LoginButton;
// import com.facebook.Request;
//import com.facebook.Request.GraphUserCallback;
// import com.facebook.Response;
// import com.facebook.Session;
// import com.facebook.SessionState;
//import com.facebook.UiLifecycleHelper;
// import com.facebook.model.GraphUser;
// import com.facebook.widget.LoginButton;
#SuppressLint("NewApi")
public class AuthenticationFragment extends Fragment {
LoginButton facebookLoginButton;
// private UiLifecycleHelper uiHelper;
String TAG = "Fragment";
Button btnLogin, btnCreateAccount;
ProgressDialog dialogPrg;
String userName = null;
// New Facebook Added
CallbackManager callbackManager;
public static final AuthenticationFragment newInstance() {
// TODO Auto-generated constructor stub
AuthenticationFragment fragment = new AuthenticationFragment();
return fragment;
}
#Override
public void onAttach(Activity activity) {
// TODO Auto-generated method stub
super.onAttach(activity);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// TODO Auto-generated method stub
View view = inflater.inflate(R.layout.authentication_layout, container,
false);
facebookLoginButton = (LoginButton) view
.findViewById(R.id.btnFacebookLogin);
facebookLoginButton.setFragment(this);
facebookLoginButton.setReadPermissions(Arrays.asList("email"));
// New added for Facebook
// Callback registration
facebookLoginButton.registerCallback(callbackManager, new FacebookCallback<LoginResult>() {
#Override
public void onSuccess(LoginResult loginResult) {
// App code
//login ok get access token
AccessToken.getCurrentAccessToken();
}
#Override
public void onCancel() {
// App code
Log.i(TAG, "facebook login canceled");
}
#Override
public void onError(FacebookException exception) {
// App code
Log.i(TAG, "facebook login failed error");
}
});
//New added for Facebook END
btnLogin = (Button) view.findViewById(R.id.btn_login);
btnCreateAccount = (Button) view.findViewById(R.id.btn_create_account);
btnLogin.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Intent intent = new Intent(getActivity(), LoginActivity.class);
startActivity(intent);
}
});
btnCreateAccount.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent intent = new Intent(getActivity(),
CreateAccountActivity.class);
startActivity(intent);
}
});
dialogPrg = new ProgressDialog(getActivity());
dialogPrg.setCanceledOnTouchOutside(false);
return view;
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// uiHelper = new UiLifecycleHelper(getActivity(), callback);
// uiHelper.onCreate(savedInstanceState);
}
// Needs to be changed
private Session.StatusCallback callback = new Session.StatusCallback() {
#Override
public void call(final Session session, final SessionState state,
final Exception exception) {
onSessionStateChange(session, state, exception);
}
};
// Needs to be changed END
private void onSessionStateChange(Session session, SessionState state,
Exception exception) {
if (state.isOpened()) {
Log.i("FB AUT FRAGMENT", "Logged in...");
} else if (state.isClosed()) {
Log.i("FB AUT FRAGMENT", "Logged out...");
}
}
// Needs to be changed
private void insertUser(Session session) {
Request.newMeRequest(session, new GraphUserCallback() {
#Override
public void onCompleted(GraphUser user, Response response) {
// TODO Auto-generated method stub
new facebookUserCheck(user).start();
}
}).executeAsync();
}
// Needs to be changed END
// Needs to be changed
private class facebookUserCheck extends Thread {
GraphUser user;
public facebookUserCheck(GraphUser user) {
// TODO Auto-generated constructor stub
this.user = user;
}
// Needs to be changed
#Override
public void run() {
// TODO Auto-generated method stub
super.run();
// TODO Auto-generated method stub
String handleInsertUser = getActivity().getResources().getString(
R.string.users_json_url)
+ "facebook_user_check";
try {
HttpClient client = new DefaultHttpClient();
HttpPost post = new HttpPost(handleInsertUser);
MultipartEntity reqEntity = new MultipartEntity();
// Needs to be changed user.getId
reqEntity.addPart("fb_id", new StringBody(user.getId()));
// Needs to be changed END
post.setEntity(reqEntity);
HttpResponse res = client.execute(post);
HttpEntity resEntity = res.getEntity();
final String response_str = EntityUtils.toString(resEntity);
if (resEntity != null) {
Log.i(TAG, response_str);
getActivity().runOnUiThread(new Runnable() {
public void run() {
try {
dialogPrg.dismiss();
JSONArray jsonArray = new JSONArray(
response_str);
if (jsonArray.length() == 1) {
JSONObject obj = jsonArray.getJSONObject(0);
User user = Ultils.parseUser(obj);
UserSessionManager userSession = new UserSessionManager(
getActivity());
userSession.storeUserSession(user);
Intent intent = new Intent(getActivity(),
HomeActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK
| Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
}
} catch (Exception e) {
LayoutInflater inflater = LayoutInflater
.from(getActivity());
View promptsView = inflater.inflate(
R.layout.username_promtps_layout, null);
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(
getActivity());
// set prompts.xml to alertdialog builder
alertDialogBuilder.setView(promptsView);
final EditText message = (EditText) promptsView
.findViewById(R.id.editTextDialogUserInput);
alertDialogBuilder
.setMessage(getResources().getString(
R.string.choose_your_user_name));
// set dialog message
alertDialogBuilder
.setCancelable(false)
.setPositiveButton(
getResources().getString(
R.string.ok_label),
new DialogInterface.OnClickListener() {
public void onClick(
DialogInterface dialog,
int id) {
if (!Validator
.validUserName(message
.getText()
.toString())) {
showDialog(getResources()
.getString(
R.string.invalid_user_name));
return;
}
userName = message
.getText()
.toString();
new facebookUserRegister(
user).start();
}
});
// create alert dialog
AlertDialog alertDialog = alertDialogBuilder
.create();
// show it
alertDialog.show();
}
}
});
}
} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
}
// Needs to be changed
private class facebookUserRegister extends Thread {
GraphUser user;
public facebookUserRegister(GraphUser user) {
// TODO Auto-generated constructor stub
this.user = user;
}
// Needs to be changed END
#Override
public void run() {
super.run();
getActivity().runOnUiThread(new Runnable() {
#Override
public void run() {
// TODO Auto-generated method stub
dialogPrg.show();
}
});
String handleInsertUser = getActivity().getResources().getString(
R.string.users_json_url)
+ "facebook_user_register";
try {
HttpClient client = new DefaultHttpClient();
HttpPost post = new HttpPost(handleInsertUser);
MultipartEntity reqEntity = new MultipartEntity();
// Needs to be changed user.getId, user.getName, user.asMap
reqEntity.addPart("fb_id", new StringBody(user.getId()));
reqEntity.addPart("fullname", new StringBody(user.getName()));
reqEntity.addPart("email", new StringBody(user.asMap().get("email").toString()));
// Needs to be changed END
reqEntity.addPart("username", new StringBody(userName));
post.setEntity(reqEntity);
HttpResponse res = client.execute(post);
HttpEntity resEntity = res.getEntity();
final String response_str = EntityUtils.toString(resEntity);
if (resEntity != null) {
Log.i(TAG, response_str);
getActivity().runOnUiThread(new Runnable() {
public void run() {
try {
dialogPrg.dismiss();
JSONObject jsonObj = new JSONObject(
response_str);
if (jsonObj.getString("ok").equals("0")) {
// show error email;
showDialog(getActivity().getResources()
.getString(R.string.email_exist));
return;
}
if (jsonObj.getString("ok").equals("1")) {
// show error username
showDialog(getActivity()
.getResources()
.getString(R.string.user_name_exist));
return;
}
if (jsonObj.getString("ok").equals("2")) {
// show unknow username
showDialog(getActivity().getResources()
.getString(R.string.login_failed));
return;
}
} catch (Exception e) {
JSONArray jsonArray;
try {
jsonArray = new JSONArray(response_str);
if (jsonArray.length() == 1) {
JSONObject obj = jsonArray
.getJSONObject(0);
User user = Ultils.parseUser(obj);
UserSessionManager userSession = new UserSessionManager(
getActivity());
userSession.storeUserSession(user);
Intent intent = new Intent(
getActivity(),
HomeActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK
| Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
}
} catch (JSONException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
showDialog(getActivity().getResources()
.getString(R.string.login_failed));
}
}
}
});
}
} catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
}
// Needs to be changed
#Override
public void onResume() {
super.onResume();
Session session = Session.getActiveSession();
if (session != null && (session.isOpened() || session.isClosed())) {
onSessionStateChange(session, session.getState(), null);
}
// uiHelper.onResume();
}
// Needs to be changed END
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
// New Facebook added
callbackManager.onActivityResult(requestCode, resultCode, data);
//New Facebook added END
// uiHelper.onActivityResult(requestCode, resultCode, data);
// Needs to be changed
if (Session.getActiveSession() != null
&& Session.getActiveSession().isOpened()) {
dialogPrg.setMessage(getActivity().getResources().getString(
R.string.loging));
dialogPrg.show();
facebookLoginButton.setEnabled(false);
insertUser(Session.getActiveSession());
}
}
// Needs to be changed END
#Override
public void onPause() {
super.onPause();
// uiHelper.onPause();
}
#Override
public void onDestroy() {
super.onDestroy();
// uiHelper.onDestroy();
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
// uiHelper.onSaveInstanceState(outState);
}
public void showDialog(String message) {
Ultils.logout(getActivity());
AlertDialog.Builder buidler = new AlertDialog.Builder(getActivity());
buidler.setMessage(message);
buidler.setPositiveButton(
getActivity().getResources().getString(R.string.ok_label),
new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
// TODO Auto-generated method
// stub
facebookLoginButton.setEnabled(true);
}
});
AlertDialog dialog = buidler.create();
dialog.show();
}
}
Use this Snippet for facebook login. Works like a charm in my app.
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import com.facebook.AppEventsLogger;
import com.facebook.FacebookAuthorizationException;
import com.facebook.FacebookOperationCanceledException;
import com.facebook.FacebookRequestError;
import com.facebook.Request;
import com.facebook.Response;
import com.facebook.Session;
import com.facebook.SessionState;
import com.facebook.UiLifecycleHelper;
import com.facebook.model.GraphObject;
import com.facebook.model.GraphPlace;
import com.facebook.model.GraphUser;
import com.facebook.widget.FacebookDialog;
import com.facebook.widget.LoginButton;
import com.facebook.widget.ProfilePictureView;
import com.ids.service.R;
import android.support.v4.app.FragmentActivity;
import android.app.AlertDialog;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.util.Log;
public class MainActivity extends FragmentActivity {
private final String PENDING_ACTION_BUNDLE_KEY = "com.facebook.samples.hellofacebook:PendingAction";
private LoginButton loginButton;
private ProfilePictureView profilePictureView;
private PendingAction pendingAction = PendingAction.NONE;
private GraphUser user;
private GraphPlace place;
private List<GraphUser> tags;
private boolean canPresentShareDialog;
private boolean canPresentShareDialogWithPhotos;
private enum PendingAction {
NONE,
POST_PHOTO,
POST_STATUS_UPDATE
}
private UiLifecycleHelper uiHelper;
private Session.StatusCallback callback = new Session.StatusCallback() {
#Override
public void call(Session session, SessionState state,
Exception exception) {
onSessionStateChange(session, state, exception);
}
};
private FacebookDialog.Callback dialogCallback = new FacebookDialog.Callback() {
#Override
public void onError(FacebookDialog.PendingCall pendingCall, Exception error, Bundle data) {
Log.d("Facebook", String.format("Error: %s", error.toString()));
}
#Override
public void onComplete(FacebookDialog.PendingCall pendingCall, Bundle data) {
Log.d("Facebook", "Success!");
}
};
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
uiHelper = new UiLifecycleHelper(this, callback);
uiHelper.onCreate(savedInstanceState);
if (savedInstanceState != null) {
String name = savedInstanceState.getString(PENDING_ACTION_BUNDLE_KEY);
pendingAction = PendingAction.valueOf(name);
}
setContentView(R.layout.activity_main);
profilePictureView = (ProfilePictureView) findViewById(R.id.profilePicture);
loginButton = (LoginButton) findViewById(R.id.login_button);
loginButton.setUserInfoChangedCallback(new LoginButton.UserInfoChangedCallback() {
#Override
public void onUserInfoFetched(GraphUser user) {
MainActivity.this.user = user;
updateUI();
// It's possible that we were waiting for this.user to be populated in order to post a
// status update.
handlePendingAction();
}
});
}
#Override
protected void onResume() {
super.onResume();
uiHelper.onResume();
// Call the 'activateApp' method to log an app event for use in analytics and advertising reporting. Do so in
// the onResume methods of the primary Activities that an app may be launched into.
AppEventsLogger.activateApp(this);
updateUI();
}
#Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
uiHelper.onSaveInstanceState(outState);
outState.putString(PENDING_ACTION_BUNDLE_KEY, pendingAction.name());
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
uiHelper.onActivityResult(requestCode, resultCode, data, dialogCallback);
}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
// Call the 'deactivateApp' method to log an app event for use in analytics and advertising
// reporting. Do so in the onPause methods of the primary Activities that an app may be launched into.
AppEventsLogger.deactivateApp(this);
}
#Override
public void onDestroy() {
super.onDestroy();
uiHelper.onDestroy();
}
private void onSessionStateChange(Session session, SessionState state, Exception exception) {
if (pendingAction != PendingAction.NONE &&
(exception instanceof FacebookOperationCanceledException ||
exception instanceof FacebookAuthorizationException)) {
new AlertDialog.Builder(MainActivity.this)
.setTitle(R.string.cancelled)
.setMessage(R.string.permission_not_granted)
.setPositiveButton(R.string.ok, null)
.show();
pendingAction = PendingAction.NONE;
} else if (state == SessionState.OPENED_TOKEN_UPDATED) {
handlePendingAction();
}
updateUI();
}
#SuppressWarnings("unused")
private void updateUI() {
Session session = Session.getActiveSession();
if (user != null) {
profilePictureView.setProfileId(user.getId());
Log.e("Name", user.getName());
}
}
#SuppressWarnings("incomplete-switch")
private void handlePendingAction() {
PendingAction previouslyPendingAction = pendingAction;
// These actions may re-set pendingAction if they are still pending, but we assume they
// will succeed.
pendingAction = PendingAction.NONE;
switch (previouslyPendingAction) {
case POST_PHOTO:
postPhoto();
break;
case POST_STATUS_UPDATE:
postStatusUpdate();
break;
}
}
private interface GraphObjectWithId extends GraphObject {
String getId();
}
private void showPublishResult(String message, GraphObject result, FacebookRequestError error) {
String title = null;
String alertMessage = null;
if (error == null) {
title = getString(R.string.success);
String id = result.cast(GraphObjectWithId.class).getId();
alertMessage = getString(R.string.successfully_posted_post, message, id);
} else {
title = getString(R.string.error);
alertMessage = error.getErrorMessage();
}
new AlertDialog.Builder(this)
.setTitle(title)
.setMessage(alertMessage)
.setPositiveButton(R.string.ok, null)
.show();
}
private FacebookDialog.ShareDialogBuilder createShareDialogBuilderForLink() {
return new FacebookDialog.ShareDialogBuilder(this)
.setName("Hello Facebook")
.setDescription("The 'Hello Facebook' sample application showcases simple Facebook integration")
.setLink("http://developers.facebook.com/android");
}
private void postStatusUpdate() {
if (canPresentShareDialog) {
FacebookDialog shareDialog = createShareDialogBuilderForLink().build();
uiHelper.trackPendingDialogCall(shareDialog.present());
} else if (user != null && hasPublishPermission()) {
final String message = getString(R.string.status_update, user.getFirstName(), (new Date().toString()));
Request request = Request
.newStatusUpdateRequest(Session.getActiveSession(), message, place, tags, new Request.Callback() {
#Override
public void onCompleted(Response response) {
showPublishResult(message, response.getGraphObject(), response.getError());
}
});
request.executeAsync();
} else {
pendingAction = PendingAction.POST_STATUS_UPDATE;
}
}
private FacebookDialog.PhotoShareDialogBuilder createShareDialogBuilderForPhoto(Bitmap... photos) {
return new FacebookDialog.PhotoShareDialogBuilder(this)
.addPhotos(Arrays.asList(photos));
}
private void postPhoto() {
Bitmap image = BitmapFactory.decodeResource(this.getResources(), R.drawable.ic_launcher);
if (canPresentShareDialogWithPhotos) {
FacebookDialog shareDialog = createShareDialogBuilderForPhoto(image).build();
uiHelper.trackPendingDialogCall(shareDialog.present());
} else if (hasPublishPermission()) {
Request request = Request.newUploadPhotoRequest(Session.getActiveSession(), image, new Request.Callback() {
#Override
public void onCompleted(Response response) {
showPublishResult(getString(R.string.photo_post), response.getGraphObject(), response.getError());
}
});
request.executeAsync();
} else {
pendingAction = PendingAction.POST_PHOTO;
}
}
private boolean hasPublishPermission() {
Session session = Session.getActiveSession();
return session != null && session.getPermissions().contains("publish_actions");
}
}
As you can read in the Facebook SDK for Android changelog in section 4.0 - March 25, 2015 the UiLifecycleHelper was removed and its functionality transferred to the CallbackManager.
Here is a tutorial which explains how to implement the login with facebook SDK 4.0.
I need to ask at the user to authorize publish permission if he dont do it.
I do it with this row of code:
//Into ShareOnFacebookFragment
Session.getActiveSession().requestNewPublishPermissions(new NewPermissionsRequest((SocialSharingActivity)getActivity(), "publish_actions"));
SocialSharingActivity is the Activity related to my Fragment (ShareOnFacebookFragment).
When I run the application the app correctly ask me the publish permission and I accept, but when I do publish I have this error in my logcat:
12-11 12:17:27.277: E/AndroidRuntime(29125): Caused by: java.lang.UnsupportedOperationException: Session: an attempt was made to request new permissions for a session that has a pending request.
Honestly my only hypotesis is that requestNewPublishPermissions run Async in background and then I have the problems when I try to publish. How I can solve this problem ? I post also my Entire fragment code
private final String TAG = "ShareFragment";
private UiLifecycleHelper uiHelper;
// To allow a Fragment to communicate up to its Activity, you can define an interface in the Fragment class and implement it within the
// Activity. The Fragment captures the interface implementation during its onAttach() lifecycle method and can then call the Interface methods in
// order to communicate with the Activity.
private Session.StatusCallback callback = new Session.StatusCallback() { //Provides asynchronous notification of Session state changes.
#Override
public void call(Session session, SessionState state,Exception exception) {
onSessionStateChange(session, state, exception);
}
};
private void onSessionStateChange(Session session, SessionState state,Exception exception) {
Log.i("CALLBACK: ", "Session state change: "+state);
}
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
uiHelper = new UiLifecycleHelper(getActivity(), callback);
uiHelper.onCreate(savedInstanceState);
};
// This makes sure that the container activity has implemented
// the callback interface. If not, it throws an exception
// try {
// mCallback = (OnHeadlineSelectedListener) activity;
// } catch (ClassCastException e) {
// throw new ClassCastException(activity.toString()
// + " must implement OnHeadlineSelectedListener");
// }
//}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
};
#Override
public void onResume() {
// TODO Auto-generated method stub
super.onResume();
uiHelper.onResume();
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
RelativeLayout myRelative = (RelativeLayout) inflater.inflate(R.layout.share_frame, container, false);
shareButton = (Button) myRelative.findViewById(R.id.shareButton);
workoutIdTextView = (TextView) myRelative.findViewById(R.id.workoutIdTextView);
objectCreatedTextView = (TextView) myRelative.findViewById(R.id.objectCreatedTextView);
actionCreatedTextView = (TextView) myRelative.findViewById(R.id.actionCreatedTextView);
return myRelative;
}
#Override
public void onSaveInstanceState(Bundle outState) {
// TODO Auto-generated method stub
super.onSaveInstanceState(outState);
uiHelper.onSaveInstanceState(outState);
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
// TODO Auto-generated method stub
super.onActivityResult(requestCode, resultCode, data);
uiHelper.onActivityResult(requestCode, resultCode, data);
}
#Override
public void onDestroy() {
// TODO Auto-generated method stub
super.onDestroy();
uiHelper.onDestroy();
}
#Override
public void onStart() {
// TODO Auto-generated method stub
super.onStart();
}
#Override
public void onActivityCreated(Bundle bundle) {
super.onActivityCreated(bundle);
Log.i(TAG, "ONACTIVITYCREATED");
SocialSharingActivity caller =(SocialSharingActivity) getActivity();
Log.w(TAG, "caller "+caller.toString());
workoutIdTextView.setText(String.valueOf(caller.getWorkoutId()));
Log.i(TAG, "Data course " + caller.getEwCourse().toString());
Log.i(TAG, "Message Run " + caller.getEwRun().toString());
ewCourseFrag = caller.getEwCourse();
ewRunFrag = caller.getEwRun();
parAct=new Bundle();
parAct.putAll(ewRunFrag.getParams());
parObj = new Bundle();
parObj.putString("access_token", APP_ACCESS_TOKEN);
gson = new Gson();
parObj.putString("object", gson.toJson(ewCourseFrag));
publishSession = Session.getActiveSession();
//------------------------------Batch HTTP request-----------------------------------------------------------------------------------------------------------------
//
//------------------------------Declaration--and--implementation--of--Callback-----------------------------------------------------------------------------------------------------------------
RequestBatch.Callback batchCallback= new RequestBatch.Callback() {
#Override
public void onBatchCompleted(RequestBatch batch) {
Log.w(TAG, "Batch completed: "+ "OK");
//
}
};
//
Request.Callback reqCreateObjCallback= new Request.Callback() {
#Override
public void onCompleted(Response response) {
if(response.getError() == null){
Log.w(TAG,"reqCreateObjCallback: "+ "OK");
objectCreatedTextView.setText("OK object");
}
else {
Log.e(TAG,"reqCreateObjCallback: "+ response.getError().toString());
Log.d(TAG, response.getError().getCategory().toString());
objectCreatedTextView.setText(response.getError().getCategory().toString());
}
//400
}
};
//
Request.Callback reqPublishCallback= new Request.Callback() {
#Override
public void onCompleted(Response response) {
if(response.getError() == null) {
Log.w(TAG, "reqPublishCallback: "+ "OK");
actionCreatedTextView.setText("OK action");
// Toast.makeText(context, "ACTION_CREATED", Toast.LENGTH_LONG).show();
}
else {
Log.e(TAG, "reqPublishCallback: "+ response.getError().toString());
Log.d(TAG, response.getError().getCategory().toString());
actionCreatedTextView.setText(response.getError().getCategory().toString());
}
}
};
//-----------------------------------------------------------------------------------------------------------------------------------------------------------------
//------------------------------Create--instance--of--RequestBatch--------------------------------------------------------------------------------------------------------
RequestBatch requestBatch= new RequestBatch();
//------------------------------Request--for-create-the-graph-object---------------------------------------------------------------------------------------------------------------
Request reqCreateObj= new Request(
publishSession,
"app/objects/fitness.course",
parObj,HttpMethod.POST); //Create a Request for a common ObiectGraph of type course
reqCreateObj.setCallback(reqCreateObjCallback); //Set the callback for the Request
reqCreateObj.setBatchEntryName("objectCreate"); //Tag the request name into the Batch with "objectCreate"
requestBatch.add(reqCreateObj); //Add the request to the batch
//------------------------------Request-for-publish-action-------------------------------------------------------------------------------------------------------------------------------
parAct.putString("course",
"{result=objectCreate:$.id}"); //Use the tag to retrieve the informations about the graph object created
//can also add scrape flag to update the object
// par2.putString("end_time", new Date(new Date().getTime()+1000*60*2).toString()); // live text test
Request reqPublish =
new Request(publishSession, //Create a request for publish an action relative to the object;
// Similarly at a phrase, an action is like "verbo", graph object
"me/fitness.runs/",parAct, //is like "complemento oggetto" and the the user is "soggetto"
HttpMethod.POST); //
reqPublish.setCallback(reqPublishCallback); //Set the callback for the Request
requestBatch.add(reqPublish); //Add the request to the batch
requestBatch.addCallback(batchCallback); //Set the callback for the Batch Request
//Check network session opened and permissions
//codice sospeso
if(Session.getActiveSession().isOpened() && hasPublishPermission() && isNetworkAvailable()) {
Toast.makeText(getActivity(), "Session is opened, I have permission, Network is On", Toast.LENGTH_LONG).show();
requestBatch.executeAsync();
}
else if (Session.getActiveSession().isOpened() && isNetworkAvailable()){
Toast.makeText(getActivity(), "I dont have Permissions: " + Session.getActiveSession().getPermissions(), Toast.LENGTH_LONG).show();
Session.getActiveSession().requestNewPublishPermissions(new NewPermissionsRequest((SocialSharingActivity)getActivity(), "publish_actions"));
Toast.makeText(getActivity(), "Permissions: " + Session.getActiveSession().getPermissions(), Toast.LENGTH_LONG).show();
}
else if (Session.getActiveSession().isOpened() && hasPublishPermission()) {
Toast.makeText(getActivity(), "Check your status connection.", Toast.LENGTH_LONG).show();
}
else {
Intent loginIntent = new Intent((SocialSharingActivity)getActivity(),FbLoginActivity.class);
startActivity(loginIntent);
}
}
private boolean isNetworkAvailable() {
ConnectivityManager connectivityManager = (ConnectivityManager)getActivity().getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo activeNetworkInfo = connectivityManager.getActiveNetworkInfo();
return activeNetworkInfo != null;
}
private boolean hasPublishPermission() {
Session session = Session.getActiveSession();
return session != null && session.getPermissions().contains("publish_actions");
}
}
I am new to the facebook sdk, so I am not really too sure why I am getting this error. I have narrowed it down to this section:
List<String> permissions = session.getPermissions();
if (!isSubsetOf(PERMISSIONS, permissions)) {
pendingPublishReauthorization = true;
Session.NewPermissionsRequest newPermissionsRequest = new Session
.NewPermissionsRequest(this, PERMISSIONS);
Here>> session.requestNewPublishPermissions(newPermissionsRequest); <<Here
return;
} //this code is located below in the publishStory() method
I followed both the Authenticate tutorial, and the Publish Feed tutorial exactly as is, with a bit of reordering to suit my needs. I am not sure what I could have possibly missed. I will post the SelectionFragment class, which I put the post status stuff to because its where a user is logged in. Just to make sure this is clear, logging in works perfectly. But when I try to click post status it does nothing. The second time I click it, it crashes. Any explanation would be most appreciated.
public class SelectionFragment extends Fragment{
private static final int REAUTH_ACTIVITY_CODE = 100;
private ProfilePictureView profilePictureView;
private TextView userNameView;
private UiLifecycleHelper uiHelper;
private Button shareButton;
private static final List<String> PERMISSIONS = Arrays.asList("publish_actions");
private static final String PENDING_PUBLISH_KEY = "pendingPublishReauthorization";
protected static final String TAG = "SelectionFragment.java";
private boolean pendingPublishReauthorization = false;
private Session.StatusCallback callback = new Session.StatusCallback() {
#Override
public void call(final Session session, final SessionState state, final Exception exception) {
onSessionStateChange(session, state, exception);
}
};
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
uiHelper = new UiLifecycleHelper(getActivity(), callback);
uiHelper.onCreate(savedInstanceState);
}//end of onCreate()
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
View view = inflater.inflate(R.layout.selection, container, false);
// Find the user's profile picture custom view
profilePictureView = (ProfilePictureView) view.findViewById(R.id.selection_profile_pic);
profilePictureView.setCropped(true);
// Find the user's name view
userNameView = (TextView) view.findViewById(R.id.selection_user_name);
//find the share button
shareButton = (Button) view.findViewById(R.id.shareButton);
shareButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
publishStory();
}
});
// Check for an open session
Session session = Session.getActiveSession();
if (session != null && session.isOpened()) {
// Get the user's data
makeMeRequest(session);
}
if (savedInstanceState != null) {
pendingPublishReauthorization =
savedInstanceState.getBoolean(PENDING_PUBLISH_KEY, false);
}
return view;
}//end of onCreateView
/*
* Private method that requests users data
* */
private void makeMeRequest(final Session session) {
// Make an API call to get user data and define a
// new callback to handle the response.
Request request = Request.newMeRequest(session,
new Request.GraphUserCallback() {
#Override
public void onCompleted(GraphUser user, Response response) {
// If the response is successful
if (session == Session.getActiveSession()) {
if (user != null) {
// Set the id for the ProfilePictureView
// view that in turn displays the profile picture.
profilePictureView.setProfileId(user.getId());
// Set the Textview's text to the user's name.
userNameView.setText(user.getName());
}
}
if (response.getError() != null) {
// Handle errors, will do so later.
}
}
});
request.executeAsync();
}
/*
* private method that will respond to session changes and call
* the makeMeRequest() method if the session's open
* */
private void onSessionStateChange(final Session session, SessionState state, Exception exception) {
if (session != null && session.isOpened()) {
// Get the user's data.
makeMeRequest(session);
}
/*The following checks if user is logged in and hides or shows the share button*/
if (state.isOpened()) {
shareButton.setVisibility(View.VISIBLE);
if (pendingPublishReauthorization &&
state.equals(SessionState.OPENED_TOKEN_UPDATED)) {
pendingPublishReauthorization = false;
publishStory();
}
} else if (state.isClosed()) {
shareButton.setVisibility(View.INVISIBLE);
}
}//end of onSessionStateChanged
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REAUTH_ACTIVITY_CODE) {
uiHelper.onActivityResult(requestCode, resultCode, data);
}
}
#Override
public void onResume() {
super.onResume();
uiHelper.onResume();
}
#Override
public void onSaveInstanceState(Bundle bundle) {
super.onSaveInstanceState(bundle);
bundle.putBoolean(PENDING_PUBLISH_KEY, pendingPublishReauthorization);
uiHelper.onSaveInstanceState(bundle);
}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
}
#Override
public void onDestroy() {
super.onDestroy();
uiHelper.onDestroy();
}
/*
* What actually publishes the status update
* */
private void publishStory() {
Session session = Session.getActiveSession();
if (session != null){
// Check for publish permissions
List<String> permissions = session.getPermissions();
if (!isSubsetOf(PERMISSIONS, permissions)) {
pendingPublishReauthorization = true;
Session.NewPermissionsRequest newPermissionsRequest = new Session
.NewPermissionsRequest(this, PERMISSIONS);
session.requestNewPublishPermissions(newPermissionsRequest);
return;
}
Bundle postParams = new Bundle();
postParams.putString("name", "Facebook SDK for Android");
postParams.putString("caption", "Build great social apps and get more installs.");
postParams.putString("description", "The Facebook SDK for Android makes it easier and faster to develop Facebook integrated Android apps.");
postParams.putString("link", "https://developers.facebook.com/android");
postParams.putString("picture", "https://raw.github.com/fbsamples/ios-3.x-howtos/master/Images/iossdk_logo.png");
Request.Callback callback= new Request.Callback() {
public void onCompleted(Response response) {
JSONObject graphResponse = response
.getGraphObject()
.getInnerJSONObject();
String postId = null;
try {
postId = graphResponse.getString("id");
} catch (JSONException e) {
Log.i(TAG,
"JSON error "+ e.getMessage());
}
FacebookRequestError error = response.getError();
if (error != null) {
Toast.makeText(getActivity()
.getApplicationContext(),
error.getErrorMessage(),
Toast.LENGTH_SHORT).show();
} else {
Toast.makeText(getActivity()
.getApplicationContext(),
postId,
Toast.LENGTH_LONG).show();
}
}
};
Request request = new Request(session, "me/feed", postParams,
HttpMethod.POST, callback);
RequestAsyncTask task = new RequestAsyncTask(request);
task.execute();
}
}//end of publishStory
private boolean isSubsetOf(Collection<String> subset, Collection<String> superset) {
for (String string : subset) {
if (!superset.contains(string)) {
return false;
}
}
return true;
}
}//end of class
Edit
Ok so I was able to finally post, but now I have figured out why its crashing still. The last method in the above class, isSubset seems to always return false, meaning it will always run, even if the publish permission was already created.
Edit 2
public class FacebookFrag extends FragmentActivity {
private static final int SPLASH = 0;
private static final int SELECTION = 1;
private static final int SETTINGS = 2;
private static final int FRAGMENT_COUNT = SETTINGS +1;
private Fragment[] fragments = new Fragment[FRAGMENT_COUNT];
private MenuItem settings;
//flag that indicates a visible activity
private boolean isResumed = false;
private UiLifecycleHelper uiHelper;
private Session.StatusCallback callback =
new Session.StatusCallback() {
#Override
public void call(Session session,
SessionState state, Exception exception) {
onSessionStateChange(session, state, exception);
}
};
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.facebook_layout);
FragmentManager fm = getSupportFragmentManager();
fragments[SPLASH] = fm.findFragmentById(R.id.splashFragment);
fragments[SELECTION] = fm.findFragmentById(R.id.selectionFragment);
fragments[SETTINGS] = fm.findFragmentById(R.id.userSettingsFragment);
FragmentTransaction transaction = fm.beginTransaction();
for(int i = 0; i < fragments.length; i++) {
transaction.hide(fragments[i]);
}
transaction.commit();
uiHelper = new UiLifecycleHelper(this, callback);
uiHelper.onCreate(savedInstanceState);
}
private void showFragment(int fragmentIndex, boolean addToBackStack) {
FragmentManager fm = getSupportFragmentManager();
FragmentTransaction transaction = fm.beginTransaction();
for (int i = 0; i < fragments.length; i++) {
if (i == fragmentIndex) {
transaction.show(fragments[i]);
} else {
transaction.hide(fragments[i]);
}
}
if (addToBackStack) {
transaction.addToBackStack(null);
}
transaction.commit();
}
private void onSessionStateChange(Session session, SessionState state, Exception exception) {
// Only make changes if the activity is visible
if (isResumed) {
FragmentManager manager = getSupportFragmentManager();
// Get the number of entries in the back stack
int backStackSize = manager.getBackStackEntryCount();
// Clear the back stack
for (int i = 0; i < backStackSize; i++) {
manager.popBackStack();
}
if (state.isOpened()) {
// If the session state is open:
// Show the authenticated fragment
showFragment(SELECTION, false);
} else if (state.isClosed()) {
// If the session state is closed:
// Show the login fragment
showFragment(SPLASH, false);
}
}
}
#Override
protected void onResumeFragments() {
super.onResumeFragments();
Session session = Session.getActiveSession();
if (session != null && session.isOpened()) {
// if the session is already open,
// try to show the selection fragment
showFragment(SELECTION, false);
} else {
// otherwise present the splash screen
// and ask the person to login.
showFragment(SPLASH, false);
}
}
#Override
public boolean onPrepareOptionsMenu(Menu menu) {
// only add the menu when the selection fragment is showing
if (fragments[SELECTION].isVisible()) {
if (menu.size() == 0) {
settings = menu.add(R.string.settings);
}
return true;
} else {
menu.clear();
settings = null;
}
return false;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
if (item.equals(settings)) {
showFragment(SETTINGS, true);
return true;
}
return false;
}
#Override
public void onResume() {
super.onResume();
uiHelper.onResume();
isResumed = true;
}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
isResumed = false;
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
uiHelper.onActivityResult(requestCode, resultCode, data);
}
#Override
public void onDestroy() {
super.onDestroy();
uiHelper.onDestroy();
}
#Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
uiHelper.onSaveInstanceState(outState);
}
}//end of class
just remove the return from your publishstory();And make sure that your session is in OPEN state when you call publishstory().
//
if(isNetworkAvailable()){
/* ~post your data only if session is in OPEN state also check
for login and internet connection*/
Session session=Session.getActiveSession();
if(session!=null){
MyLog.w("session state",session.getState().toString());
if(session.getState()==SessionState.OPENED){
publishStory();
}else{
showAlertDialog("Unable to Share");
}
}else{
showAlertDialog("Please login first!");
}
}else{
showAlertDialog("Problem occured with your internet connection");
}
remove return statement
if (!isSubsetOf(PERMISSIONS, permissions)) {
pendingPublishReauthorization = true;
Session.NewPermissionsRequest newPermissionsRequest = new Session
.NewPermissionsRequest(this, PERMISSIONS);
session.requestNewPublishPermissions(newPermissionsRequest);
`Remove this===>` return;
}
Normally, when you got UnsupportedOperationException, it means that the device cannot find the method that used in your app.
Something you need to check:
The Android version of emulator or test device must be greater than the Min SDK?
All the library is included and exported correctly?
when I install my app via ADB via Eclipse, then the facebook logon as well as publishing to the wall of the user works (using facebook SDK 3.0), but when I package my app and then install that app, then the facebook logon does not work. I get the fragment with a logon button, when I push the logon button, then it shows the dialog that the app wants to have access to my public profile and friendlist. When I click ok it goes back to the fragment with the login button.
My question is: What should I change to make the facebook SDK integration work during deployment time as well?
my code of the fragment (erased non-relevant parts):
public class Fragment_shareFacebook extends SherlockFragment {
Context context; //context and fields:
View v;
private Button shareButton;
private MainActvityCommunicatorIntentBasedLeaveManagement intentleaveset;
private EditText toshareText;
private TextView textInstructionsOrLink, sharedText, fb_share_title_preview, fb_share_text_preview, sharesubsubtitle;
private ViewSwitcher switcher;
private LinearLayout fb_preview_keeper, mainlayoutholderfbshare, loggedinscreen;
String subject, content;
private boolean switched;
private UiLifecycleHelper uiHelper;
private static final int REAUTH_ACTIVITY_CODE = 100;
private UserSettingsFragment usersetting;
private static final List<String> PERMISSIONS = Arrays.asList("publish_actions");
private Session.StatusCallback callback =
new Session.StatusCallback() {
#Override
public void call(Session session,
SessionState state, Exception exception) {
onSessionStateChange(session, state, exception);
}
};
/**
* empty constructor
*/
public Fragment_shareFacebook(){
}
#Override
/**
* initialize the intentleaveset to inform main that we have an intent based leave standing by
*/
public void onAttach(Activity activity) {
super.onAttach(activity);
context = getActivity();
intentleaveset=(MainActvityCommunicatorIntentBasedLeaveManagement) context;
}
#Override
/**
* get the content that needs to be shared, also retrieve the pendingPublishReauthorization if necessary
*/
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
this.setHasOptionsMenu(true);
uiHelper = new UiLifecycleHelper(this.getActivity(), callback);
uiHelper.onCreate(savedInstanceState);
subject = getArguments().getString("subject");
content = getArguments().getString("text");
}
#Override
public void onResume() {
super.onResume();
uiHelper.onResume();
Session session = Session.getActiveSession();
this.onSessionStateChange(session, session.getState(), null);
}
#Override
public void onPause() {
super.onPause();
uiHelper.onPause();
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if(requestCode==REAUTH_ACTIVITY_CODE){
uiHelper.onActivityResult(requestCode, resultCode, data);
}
}
#Override
public void onDestroy() {
super.onDestroy();
uiHelper.onDestroy();
}
#Override
public void onDestroyView(){
//note: we have to remove the fragment again!
try{
FragmentTransaction transaction = this.getActivity().getSupportFragmentManager().beginTransaction();
transaction.remove(usersetting);
transaction.commit();
}catch(Exception e){
}
super.onDestroyView();
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
uiHelper.onSaveInstanceState(outState);
}
//hvg: dze even disecten.
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
v = inflater.inflate(R.layout.fragment_facebook_share, container, false);
textInstructionsOrLink = (TextView) v.findViewById(R.id.textInstructionsOrLink);
fb_share_title_preview= (TextView) v.findViewById(R.id.fbsharetitlepreview);
fb_share_text_preview= (TextView) v.findViewById(R.id.fbsharetextpreview);
sharesubsubtitle=(TextView) v.findViewById(R.id.sharesubsubtitle);
loggedinscreen=(LinearLayout) v.findViewById(R.id.loggedinscreen);
usersetting=(UserSettingsFragment) this.getActivity().getSupportFragmentManager().findFragmentById(R.id.userSettingsFragment);
//authButton = (LoginButton) v.findViewById(R.id.authButton);
shareButton = (Button) v.findViewById(R.id.shareButton);
//usernamefield= (TextView) v.findViewById(R.id.selection_user_name);
toshareText = (EditText) v.findViewById(R.id.toshareText);
fb_preview_keeper= (LinearLayout) v.findViewById(R.id.fb_preview_keeper);
mainlayoutholderfbshare = (LinearLayout) v.findViewById(R.id.mainlayoutholderfbshare);
switcher=(ViewSwitcher)v.findViewById(R.id.fb_switcher);
mainlayoutholderfbshare.setOnTouchListener(new View.OnTouchListener() {
#Override
public boolean onTouch(View v, MotionEvent event) {
// TODO Auto-generated method stub
if(toshareText.isFocused()){
Log.i("Focussed", "--" + event.getX() + " : " + event.getY() + "--");
if (toshareText.isFocused()) {
Rect outRect = new Rect();
toshareText.getGlobalVisibleRect(outRect);
if (!outRect.contains((int)event.getRawX(), (int)event.getRawY())) {
toshareText.clearFocus();
InputMethodManager imm = (InputMethodManager) v.getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
}
}
}
Log.i("X-Y coordinate", "--" + event.getX() + " : " + event.getY() + "--");
//Toast.makeText(getBaseContext(), "Clicked", Toast.LENGTH_SHORT).show();
return false;
}
});
//toshareText.setText(content);
switcher=(ViewSwitcher) v.findViewById(R.id.fb_switcher);
sharedText=(TextView) v.findViewById(R.id.sharedText);
if(switcher.getDisplayedChild()==0){
switched=false;
}else{
switched=true;
}
//note that we need a custom onclicklistener to share the story to fb
shareButton.setOnClickListener(new OnClickListener(){
#Override
public void onClick(View v) {
intentleaveset.setIntentleave(true);
publishStory();
}
});
//note to main: we are leaving with an intent!
intentleaveset.setIntentleave(true);
Log.d("fsf: leaveintent","settrue");
Session session = Session.getActiveSession();
SessionState state = Session.getActiveSession().getState();
onSessionStateChange(session, state, null);
return v;
}
private void onSessionStateChange(Session session, SessionState state, Exception exception) {
// Only make changes if the activity is visible
intentleaveset.setIntentleave(true);
Log.d("switcher-init", Integer.toString(switcher.getDisplayedChild()));
if (state.isOpened()) {
// If the session state is open:
// Show the authenticated fragment
shareButton.setVisibility(View.VISIBLE);
toshareText.setVisibility(View.VISIBLE);
fb_preview_keeper.setVisibility(View.VISIBLE);
LayoutParams params = fb_preview_keeper.getLayoutParams();
params.height=LayoutParams.WRAP_CONTENT;
params.width=LayoutParams.MATCH_PARENT;
fb_preview_keeper.setLayoutParams(params);
params=shareButton.getLayoutParams();
params.height=LayoutParams.WRAP_CONTENT;
params.width=LayoutParams.MATCH_PARENT;
shareButton.setLayoutParams(params);
params=toshareText.getLayoutParams();
params.width=LayoutParams.MATCH_PARENT;
params.height=LayoutParams.WRAP_CONTENT;
toshareText.setLayoutParams(params);
toshareText.setMinLines(3);
toshareText.setScroller(new Scroller(context));
toshareText.setVerticalScrollBarEnabled(true);
fb_share_title_preview.setText(subject);
fb_share_text_preview.setText(getString(R.string.facebook_share_subtitle).concat("\n \n").concat(content));
if(!switched){
textInstructionsOrLink.setText(getString(R.string.facebookexplanationafterlgoong));
}else{
textInstructionsOrLink.setText(getString(R.string.facebookexplanationaftershared));
if(switcher.getDisplayedChild()!=1){
switcher.showNext();
}
/*
if(switcher.getDisplayedChild()==1){
switcher.showPrevious();
}else{
switcher.showNext();
}
*/
}
params=loggedinscreen.getLayoutParams();
params.height=LayoutParams.WRAP_CONTENT;
loggedinscreen.setLayoutParams(params);
sharesubsubtitle.setFocusable(true);
sharesubsubtitle.requestFocus();
} else {
// If the session state is closed:
// Show the login fragment
if(switcher.getDisplayedChild()==1){
switcher.showPrevious();
}
switched=false;
shareButton.setVisibility(View.INVISIBLE);
//shareButton.setHeight(0);
toshareText.setVisibility(View.INVISIBLE);
//toshareText.setHeight(0);
//LayoutParams params = switcher.getLayoutParams();
//params.height=0;
//params.width=params.MATCH_PARENT;
//switcher.setLayoutParams(params);
//fb_preview_keeper.setVisibility(View.INVISIBLE);
//params = fb_preview_keeper.getLayoutParams();
//params.height=0;
//params.width=params.MATCH_PARENT;
//fb_preview_keeper.setLayoutParams(params);
LayoutParams params=loggedinscreen.getLayoutParams();
params.height=0;
loggedinscreen.setLayoutParams(params);
sharedText.setText("");
textInstructionsOrLink.setText(this.getResources().getString(R.string.facebookexplainbeforelogon));
}
}
private void publishStory() {
Session session = Session.getActiveSession();
if (session != null){
// Check for publish permissions
List<String> permissions = session.getPermissions();
if (!isSubsetOf(PERMISSIONS, permissions)) {
Session.NewPermissionsRequest newPermissionsRequest = new Session
.NewPermissionsRequest(this, PERMISSIONS)
.setRequestCode(REAUTH_ACTIVITY_CODE);
session.requestNewPublishPermissions(newPermissionsRequest);
//session.reauthorizeForPublish(newPermissionsRequest);
return;
}
Bundle postParams = new Bundle();
postParams.putString("name", subject);
postParams.putString("caption", getString(R.string.facebook_share_subtitle));
postParams.putString("description", content);
if(toshareText.getText()!=null){
postParams.putString("message", toshareText.getText().toString());
}else{
postParams.putString("message", " ");
}
postParams.putString("link", "http://www.thewonderweeks.com");
postParams.putString("picture", "www.thewonderweeks.com/apple-touch-icon-114x114.png");
Request.Callback callback= new Request.Callback() {
public void onCompleted(Response response) {
JSONObject graphResponse;
try{
graphResponse = response
.getGraphObject()
.getInnerJSONObject();
}catch (Exception e){
if(e.getMessage()!=null){
Log.d("errorinFBcallback", e.getMessage());
}
return ;
}
String postId = null;
try {
postId = graphResponse.getString("id");
} catch (JSONException e) {
Log.i("errormessagefacebookfragmenthtingy",
"JSON error "+ e.getMessage());
}
FacebookRequestError error = response.getError();
if (error != null) {
Toast.makeText(getActivity()
.getApplicationContext(),
error.getErrorMessage(),
Toast.LENGTH_SHORT).show();
} else {
Log.d("post id of posted material", postId);
shareButton.setVisibility(View.INVISIBLE);
if(switcher.getDisplayedChild()!=1){
switcher.showNext();
}
switched=true;
sharedText.setText(getString(R.string.successhare).concat(" ").concat(toshareText.getText().toString()));
textInstructionsOrLink.setText(getString(R.string.facebookexplanationaftershared));
}
}
};
Request request = new Request(session, "me/feed", postParams,
HttpMethod.POST, callback);
RequestAsyncTask task = new RequestAsyncTask(request);
task.execute();
}
}
I assume you followed the facebook developers tutorial. If so, you use this command to produce your key
keytool -exportcert -alias androiddebugkey -keystore ~/.android/debug.keystore | openssl sha1 -binary | openssl base64
You must also create a key with release keystore and register it to facebook.