Android - Facebook SDK 3 - 如何在没有LoginButton的情况下以编程方式登录

urS*_*Sus 39 android login button facebook-android-sdk

我正在编写一个与Facebook SDK集成的应用程序,以分享一些(字符串)内容作为墙贴.现在,我让HelloFacebookSample工作了.但是它使用LoginButton来记录用户.

我不希望这样.我想要做的就是点击操作栏中的我的分享按钮并分享到Facebook.因此,我想以编程方式登录,我试图模拟LoginButton的功能,但到目前为止还没有成功.我明白了

12-06 15:34:33.180:E/AndroidRuntime(19493):java.lang.UnsupportedOperationException:Session:尝试重新授权具有待处理请求的会话.

公共类MainActivity扩展了FacebookActivity {

@SuppressWarnings("serial")
private static final List<String> PERMISSIONS = new ArrayList<String>() {
    {
        add("publish_actions");
    }
};
private final int REAUTHORIZE_ACTIVITY = 3;
private Button postStatusUpdateButton;
private PendingAction pendingAction = PendingAction.NONE;

private enum PendingAction {
    NONE, POST_PHOTO, POST_STATUS_UPDATE
}

/**
 * Called when the activity is first created.
 */
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    postStatusUpdateButton = (Button) findViewById(R.id.postStatusUpdateButton);
    postStatusUpdateButton.setOnClickListener(new View.OnClickListener() {
        public void onClick(View view) {
            Log.d("MainActivity", "onClick");
            onClickPostStatusUpdate();
        }

    });

}

@Override
protected void onSessionStateChange(SessionState state, Exception exception) {
    super.onSessionStateChange(state, exception);
}

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();
    }

    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder.setTitle(title).setMessage(alertMessage).setPositiveButton(getString(R.string.ok), null);
    builder.show();
}

private void onClickPostStatusUpdate() {
    Log.d("MainActivity", "onClickPostStatusUpdate");
    performPublish(PendingAction.POST_STATUS_UPDATE);
}

private boolean hasPublishPermission() {
    Session session = Session.getActiveSession();
    return session != null && session.getPermissions().contains("publish_actions");
}

private void performPublish(PendingAction action) {
    Log.d("MainActivity", "peformPublish");

    Session session = Session.getActiveSession();

    if (session == null) {
        session = new Session.Builder(this).setApplicationId("xxx").build();
        Session.setActiveSession(session);
    }

    if (!session.isOpened()) {
        Session.OpenRequest openRequest = new Session.OpenRequest(this);
        openRequest.setPermissions(PERMISSIONS);
        openRequest.setLoginBehavior(SessionLoginBehavior.SSO_WITH_FALLBACK);
        session.openForPublish(openRequest);
    }

    if (session != null) {
        // postStatusUpdate();
        pendingAction = action;
        if (hasPublishPermission()) {
            // We can do the action right away.
            handlePendingAction();
            // postStatusUpdate();
        } else {
            // We need to reauthorize, then complete the action when we get
            // called back.
            Session.ReauthorizeRequest reauthRequest = new Session.ReauthorizeRequest(this, PERMISSIONS)
                    .setRequestCode(REAUTHORIZE_ACTIVITY).setLoginBehavior(SessionLoginBehavior.SSO_WITH_FALLBACK);
            session.reauthorizeForPublish(reauthRequest);
        }
    }
}

@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_STATUS_UPDATE:
        postStatusUpdate();
        break;
    }
}

private void postStatusUpdate() {
    // if (user != null && hasPublishPermission()) {
    if (hasPublishPermission()) {
        // final String message = getString(R.string.status_update,
        // user.getFirstName(), (new Date().toString()));
        final String message = "kks uz nemam nervy";
        Request request = Request.newStatusUpdateRequest(Session.getActiveSession(), message,
                new Request.Callback() {
                    @Override
                    public void onCompleted(Response response) {
                        showPublishResult(message, response.getGraphObject(), response.getError());
                    }
                });
        Request.executeBatchAsync(request);
    } else {
        pendingAction = PendingAction.POST_STATUS_UPDATE;
    }
}

@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    Log.d("MainActivity", "onActivityResult");
    Session.getActiveSession().onActivityResult(this, requestCode, resultCode, data);
}
Run Code Online (Sandbox Code Playgroud)

}

好吧,这仍然是HelloFacebookSample项目,我试图弯曲正确的方式.我唯一使用的是performPublish方法,创建会话的东西.

希望有一个更简单的方法!PS:我正在使用Facebook SDK 3

Min*_* Li 21

你发布了整个活动的内容吗?

您还需要覆盖onActivityResult,并将值传递给Session.getActiveSession().onActivityResult(...).否则,会话将不知道用户已授权您的应用程序,这就是您看到错误的原因(会话认为仍有待处理的身份验证请求,这就是您无法重新授权发布的原因).

  • 就个人而言,我认为新的API或示例/教程可能非常糟糕.至少在我眼前.最后,我在我的应用程序中复制了整个美味的教程,以完成我想做的事情,95%的教程处理片段,布局,活动以及与核心点无关的其他内容:制作该API工作.什么应该是容易变得非常复杂,没有任何真正的需要.我不知道他们是否真的会放弃已弃用的Facebook对象,而不会让事情变得更清晰. (77认同)
  • 花了2天时间才找到这个答案,这个步骤应该在他们的教程中说明 (2认同)

sro*_*mku 18

因为我和@ Beppi对@Ming Li的评论赞不绝口,因为我和我在应用程序中使用Facebook SDK,因此我决定创建更简化的API级别,这是基于最新的Facebook SDK 3.0.b.

开源库:android-simple-facebook
https://github.com/sromku/android-simple-facebook

对于你的问题: How to login programatically?

  1. 设置登录/注销侦听器

    // set login / logout listener
    OnLoginOutListener onLoginOutListener = new SimpleFacebook.OnLoginOutListener()
    {
    
        @Override
        public void onFail()
        {
            Log.w(TAG, "Failed to login");
        }
    
        @Override
        public void onException(Throwable throwable)
        {
            Log.e(TAG, "Bad thing happened", throwable);
        }
    
        @Override
        public void onThinking()
        {
            // show progress bar or something to the user while login is happening
            Log.i(TAG, "In progress");
        }
    
        @Override
        public void onLogout()
        {
            // change the state of the button or do whatever you want
            Log.i(TAG, "Logged out");
        }
    
        @Override
        public void onLogin()
        {
            // change the state of the button or do whatever you want
            Log.i(TAG, "Logged in");
        }
    };
    
    // set the listener
    mSimpleFacebook.setLogInOutListener(onLoginOutListener);
    
    Run Code Online (Sandbox Code Playgroud)
  2. 点击任何视图,只需调用login(Activity)方法

    mSimpleFacebook.login(MainActivity.this);
    
    Run Code Online (Sandbox Code Playgroud)


  3. 注销通话logout()方法.像这样:

    mSimpleFacebook.logout();
    
    Run Code Online (Sandbox Code Playgroud)

如何在登录前设置权限,请在此处查看非常友好的解释.

希望它对某人有帮助:)

  • 谢谢.Facebook SDK是/并且将永远是非常糟糕的.我不知道建筑师在设计API时的想法,但他显然有一个非常奇怪的愿景.结果是许多糟糕的Android应用程序经常(和随机)失败或抛出神秘的消息. (4认同)
  • 真有用的库!节省了我很多时间.感谢您提供. (2认同)