Android Facebook登录

时间:2020-02-23 14:28:55  来源:igfitidea点击:

今天,我们将学习如何将Facebook登录信息集成到android应用程序中。
您一定已经将Facebook登录视为在许多应用程序中创建帐户的更简便方法。

Android Facebook登录

许多应用程序使用"使用Facebook登录"在其应用程序中注册用户。
为了使用Facebook登录,我们必须为与Facebook服务器通信的android应用程序使用唯一的ID。

让我们从创建一个新的空Android Studio项目开始。

现在,在编写任何代码之前,我们需要注册我们的应用程序,如下所示。

注册您的Facebook应用程序

使用您的Facebook帐户登录到:https://developers.facebook.com/apps/。

现在创建一个新的应用程序。
并设置应用名称和电子邮件ID,如下图所示。

注意:Facebook不允许我们设置包含关键字fb/facebook等的应用程序名称。
因此,我们将应用程序名称设置为TestTutorial。
我们需要在Android Studio项目的strings.xmlapp_id字符串中设置相同的名称。

您将在下一个屏幕中看到仪表板。
选择" Facebook登录设置",然后选择平台作为Android,如下图所示。

选择Android

在下一个屏幕上,而不是下载Facebook SDK,而是使用gradle依赖项导入SDK。
为此,请在您的" app"的" build.gradle"中添加以下依赖项。

buildscript { 
repositories {
mavenCentral()
}
}

使用最新版本的SDK依赖项。

implementation 'com.facebook.android:facebook-android-sdk:4.31.0'

要检查sdk是否成功添加到我们的项目中,请在您的MainActivity.java类文件中添加以下import语句,如下所示。
如果没有错误,则说明构建成功。

import com.facebook.FacebookSdk;
import com.facebook.appevents.AppEventsLogger;

添加您的Facebook应用程序ID需要在我们的Android Studio项目中的strings.xml中添加Facebook开发人员应用程序仪表板上存在的应用程序ID。

<string name="facebook_app_id">894882580618030</string>

输入您的包名称和默认活动名称,并使用完全限定的路径,如下所示。
保存后,单击"使用此程序包名称"进行确认。
小号

下一个窗口要求设置密钥哈希。
这可以通过在mac terminal/windows cmd上运行以下命令来完成:

//Mac cmd
keytool -exportcert -alias androiddebugkey -keystore ~/.android/debug.keystore | openssl sha1 -binary | openssl base64

//Windows cmd
keytool -exportcert -alias androiddebugkey -keystore "C:\Users\USERNAME\.android\debug.keystore" | "PATH_TO_OPENSSL_LIBRARY\bin\openssl" sha1 -binary | "PATH_TO_OPENSSL_LIBRARY\bin\openssl" base64

将哈希密钥复制并粘贴到下面的"密钥哈希"字段中。
您需要为运行此应用程序的每个设备提供密钥哈希,直到它处于开发模式为止。

在下一个网段上启用单点登录。

返回Android Studio,在strings.xml文件中添加以下行:

<string name="fb_login_protocol_scheme">fb204127990172423</string>

后面跟着fb的数字是我们上面的APP ID。

通过在列表元素中添加以下行,在AndroidManifest.xml文件中启用互联网权限。

<uses-permission android:name="android.permission.INTERNET"

现在,在列表中的application标签内添加以下代码。

<meta-data android:name="com.facebook.sdk.ApplicationId" 
      android:value="@string/facebook_app_id"
  
  <activity android:name="com.facebook.FacebookActivity"
      android:configChanges=
              "keyboard|keyboardHidden|screenLayout|screenSize|orientation"
      android:label="@string/app_name" 
  <activity
      android:name="com.facebook.CustomTabActivity"
      android:exported="true">
      <intent-filter>
          <action android:name="android.intent.action.VIEW" 
          <category android:name="android.intent.category.DEFAULT" 
          <category android:name="android.intent.category.BROWSABLE" 
          <data android:scheme="@string/fb_login_protocol_scheme" 
      </intent-filter>
  </activity>

现在完成注册和设置,让我们进入业务端。
在以下应用中,我们将添加一个带Facebook登录名的按钮,单击该按钮即可检索并显示用户的姓名,电子邮件和个人资料图片。
我们将看到Facebook SDK如何完成所有这一切。

Android Facebook集成代码

下面给出了" activity_main.xml"布局文件的代码。

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="https://schemas.android.com/apk/res/android"
  xmlns:app="https://schemas.android.com/apk/res-auto"
  xmlns:tools="https://schemas.android.com/tools"
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:background="#222"
  android:gravity="center"
  android:orientation="vertical"
  tools:context="com.theitroad.loginwithfbexample.MainActivity">

  <ImageView
      android:id="@+id/imageView"
      android:src="@mipmap/ic_launcher"
      android:layout_width="100dp"
      android:layout_height="100dp" 

  <TextView
      android:id="@+id/txtUsername"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:text="Username"
      android:padding="8dp"
      android:textColor="#FFF" 

  <TextView
      android:id="@+id/txtEmail"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:text="Email Address"
      android:padding="8dp"
      android:textColor="#FFF" 

  <com.facebook.login.widget.LoginButton
      android:id="@+id/login_button"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:paddingBottom="15dp"
      android:paddingTop="15dp"
      app:layout_constraintBottom_toBottomOf="parent"
      app:layout_constraintLeft_toLeftOf="parent"
      app:layout_constraintRight_toRightOf="parent"
      app:layout_constraintTop_toTopOf="parent" 

</LinearLayout>

我们将布局更改为LinearLayout,以垂直堆叠视图。

下面给出了MainActivity.java类的代码。

package com.theitroad.loginwithfbexample;

import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.widget.ImageView;
import android.widget.TextView;

import com.facebook.AccessToken;
import com.facebook.CallbackManager;
import com.facebook.FacebookCallback;
import com.facebook.FacebookException;
import com.facebook.GraphRequest;
import com.facebook.GraphResponse;
import com.facebook.Profile;
import com.facebook.login.LoginResult;
import com.facebook.login.widget.LoginButton;
import com.squareup.picasso.Picasso;

import org.json.JSONException;
import org.json.JSONObject;

import java.util.Arrays;

public class MainActivity extends AppCompatActivity {

  LoginButton loginButton;
  CallbackManager callbackManager;
  ImageView imageView;
  TextView txtUsername, txtEmail;

  @Override
  protected void onCreate(Bundle savedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.activity_main);

      loginButton = findViewById(R.id.login_button);
      imageView = findViewById(R.id.imageView);
      txtUsername = findViewById(R.id.txtUsername);
      txtEmail = findViewById(R.id.txtEmail);

      boolean loggedOut = AccessToken.getCurrentAccessToken() == null;

      if (!loggedOut) {
          Picasso.with(this).load(Profile.getCurrentProfile().getProfilePictureUri(200, 200)).into(imageView);
          Log.d("TAG", "Username is: " + Profile.getCurrentProfile().getName());

          //Using Graph API
          getUserProfile(AccessToken.getCurrentAccessToken());
      }

      loginButton.setReadPermissions(Arrays.asList("email", "public_profile"));
      callbackManager = CallbackManager.Factory.create();

      loginButton.registerCallback(callbackManager, new FacebookCallback<LoginResult>() {
          @Override
          public void onSuccess(LoginResult loginResult) {
              //App code
              //loginResult.getAccessToken();
              //loginResult.getRecentlyDeniedPermissions()
              //loginResult.getRecentlyGrantedPermissions()
              boolean loggedIn = AccessToken.getCurrentAccessToken() == null;
              Log.d("API123", loggedIn + " ??");

          }

          @Override
          public void onCancel() {
              //App code
          }

          @Override
          public void onError(FacebookException exception) {
              //App code
          }
      });

  }

  @Override
  protected void onActivityResult(int requestCode, int resultCode, Intent data) {
      callbackManager.onActivityResult(requestCode, resultCode, data);
      super.onActivityResult(requestCode, resultCode, data);
  }

  private void getUserProfile(AccessToken currentAccessToken) {
      GraphRequest request = GraphRequest.newMeRequest(
              currentAccessToken, new GraphRequest.GraphJSONObjectCallback() {
                  @Override
                  public void onCompleted(JSONObject object, GraphResponse response) {
                      Log.d("TAG", object.toString());
                      try {
                          String first_name = object.getString("first_name");
                          String last_name = object.getString("last_name");
                          String email = object.getString("email");
                          String id = object.getString("id");
                          String image_url = "https://graph.facebook.com/" + id + "/picture?type=normal";

                          txtUsername.setText("First Name: " + first_name + "\nLast Name: " + last_name);
                          txtEmail.setText(email);
                          Picasso.with(MainActivity.this).load(image_url).into(imageView);

                      } catch (JSONException e) {
                          e.printStackTrace();
                      }

                  }
              });

      Bundle parameters = new Bundle();
      parameters.putString("fields", "first_name,last_name,email,id");
      request.setParameters(parameters);
      request.executeAsync();

  }
}

在上面的代码中:

  • Facebook SDK自动在该类中初始化。
    因此,无需显式初始化它。

  • 我们已将" readPermissions"设置为电子邮件和public_profile。
    通常,Facebook默认提供三个权限:"电子邮件","公共档案"和"用户朋友"。
    其中" user_friends"将显示使用此应用的朋友。

  • 我们实例化一个CallBackManager,以在LoginButton单击时调用注册回调。

  • 如果单击按钮的结果成功,则返回LoginResult类。
    通过它,我们可以访问访问令牌,已授予和已撤消的权限。

  • " onActivityResult"获取登录的响应,并将其传递给" registerCallback"方法。

  • " AccessToken"会隐式自动保存在应用程序数据(SharedPreferences)中。

因此,每次创建活动时,我们都调用AccessToken.getCurrentAccessToken()
如果为空,则用户必须再次登录。

  • 同样,如果Profile类返回当前用户,我们可以通过该用户检索配置文件名称,图片。

  • Facebook Graph API用于检索用户信息。
    它通过将一束参数作为键传递给GraphRequest来工作。
    在执行GraphRequest时,如果它们满足权限,则应基于指定的键返回相关的信息值。
    结果以JSON形式返回。

  • 我们已使用毕加索在ImageView中显示图片网址。

为此,我们需要添加以下依赖项:

监听LoginButton单击时的更改AccessTokenTracker使监听按钮单击时的更改成为可能。
accessToken2是最新的访问令牌。
accessToken是较旧的。

Android Facebook登录应用程序输出

下面给出了上面应用程序的输出。

注意:如果出现这样的错误:

将您在各自屏幕中提到的哈希添加到Facebook开发者页面上的"应用程序仪表盘"中。
您需要在开发模式下使用通过Facebook登录的方式为所有此类设备添加哈希值。

为Facebook集成添加更多权限

要在您的应用程序中添加和使用更多权限,请转到Facebook开发人员页面上仪表板上的"应用程序查看"部分。
每个新许可都必须首先由Facebook批准。