Tôi đang sử dụng "Đăng nhập bằng Google" trong ứng dụng của mình. Do đó tôi sử dụng lớp GoogleApiClient để nhận email người dùng và mã thông báo ID mà tôi cần cho chương trình phụ trợ của mình.Đăng nhập im lặng để truy xuất mã thông báo với GoogleApiClient
Khi người dùng đăng nhập, sau đó tôi có quyền truy cập vào một hoạt động (tất nhiên) và tôi sử dụng Hoạt động mà để cho các GoogleApiClient xử lý các công cụ UI vòng đời bằng cách gọi builder.enableAutoManage (myActivity, ...)
Điều này hoạt động tốt.
Tuy nhiên, ở giai đoạn sau (vài ngày sau), tôi cần lấy mã thông báo mới (vì một lý do nào đó tôi sẽ không đi sâu vào đây). Tôi muốn nhận được mã thông báo này âm thầm mà không có sự tương tác của người dùng. Tuy nhiên, tại thời điểm trong mã của tôi, nơi tôi cần mã thông báo mới này, tôi không có quyền truy cập vào bất kỳ cá thể Hoạt động nào. Điều đó có nghĩa là tôi không thể để thực hiện cuộc gọi được đề cập ở trên, tức là "builder.enableAutoManage". Và tôi đã thấy rằng nếu tôi không thực hiện cuộc gọi đó, thì thông tin đăng nhập im lặng dường như không hoạt động.
Tôi đã đính kèm mã bên dưới. Bây giờ, hãy xem phương thức "silentLogin". Miễn là mã thông báo mà tôi đã nhận được khi người dùng đã đăng nhập thực tế, nhỏ hơn một giờ, thì câu lệnh "pendingResult.isDone" sẽ trả về true và có thể nhận được mã thông báo được lưu trong bộ nhớ cache. Tuy nhiên, nếu mã thông báo mà tôi đã nhận được khi người dùng đã đăng nhập thực tế, cũ hơn một giờ, thì cuộc gọi "pendingResult.setResultCallback" được thực hiện NHƯNG phương thức "onResult" KHÔNG BAO GIỜ ĐƯỢC GỌI và tôi không thể nhận được thông tin mới mã thông báo. Vấn đề này không xảy ra nếu tôi làm chính xác như vậy từ một hoạt động (và bằng cách đó cũng thực hiện cuộc gọi "builder.enableAutoManage"). Vì vậy, không ai biết những gì tôi đang làm sai và quan trọng hơn - làm thế nào để giải quyết vấn đề này và nhận được một mã thông báo mới mà không cần truy cập vào một thể hiện hoạt động? Không.
Tôi đang sử dụng com.google.android.gms: play-dịch vụ-auth: 8.4.0
package com.google.samples.quickstart.signin;
import android.content.Context;
import android.os.Bundle;
import android.util.Log;
import com.google.android.gms.auth.api.Auth;
import com.google.android.gms.auth.api.signin.GoogleSignInAccount;
import com.google.android.gms.auth.api.signin.GoogleSignInOptions;
import com.google.android.gms.auth.api.signin.GoogleSignInResult;
import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.Scopes;
import com.google.android.gms.common.api.GoogleApiClient;
import com.google.android.gms.common.api.OptionalPendingResult;
import com.google.android.gms.common.api.ResultCallback;
import com.google.android.gms.common.api.Scope;
/**
* Use this class to login with google account using the OpenId oauth method.
*/
public class GoogleLoginStackOverflow {
private static final String TAG = GoogleLoginIdToken.class.getName();
private static final String SERVER_CLIENT_ID = "XXXXXXXXXXXXXXXXXXXXXXXX.apps.googleusercontent.com";
private GoogleApiClient mGoogleApiClient;
private Context mContext;
private GoogleLoginStackOverflow(Context appContext) {
this.mContext = appContext;
createGoogleClient();
}
/**
* Performs a silent sign in and fetch a token.
*
* @param appContext Application context
*/
public static void silentLogin(Context appContext) {
GoogleLoginStackOverflow googleLoginIdToken = new GoogleLoginStackOverflow(appContext);
googleLoginIdToken.silentLogin();
}
private void createGoogleClient() {
GoogleSignInOptions gso = new GoogleSignInOptions.Builder(GoogleSignInOptions.DEFAULT_SIGN_IN)
.requestProfile()
.requestScopes(new Scope(Scopes.PROFILE))
.requestIdToken(SERVER_CLIENT_ID)
.requestEmail()
.build();
mGoogleApiClient = new GoogleApiClient.Builder(mContext)
.addOnConnectionFailedListener(new GoogleApiClient.OnConnectionFailedListener() {
@Override
public void onConnectionFailed(ConnectionResult connectionResult) {
System.out.println("onConnectionFailed = " + connectionResult);
onSilentLoginFinished(null);
}
})
.addConnectionCallbacks(new GoogleApiClient.ConnectionCallbacks() {
@Override
public void onConnected(Bundle bundle) {
System.out.println("onConnected bundle = " + bundle);
onSilentLoginFinished(null);
}
@Override
public void onConnectionSuspended(int i) {
System.out.println("onConnectionSuspended i = " + i);
onSilentLoginFinished(null);
}
}).addApi(Auth.GOOGLE_SIGN_IN_API, gso)
.build();
}
private void silentLogin() {
OptionalPendingResult<GoogleSignInResult> pendingResult = Auth.GoogleSignInApi.silentSignIn(mGoogleApiClient);
if (pendingResult != null) {
if (pendingResult.isDone()) {
// If the user's cached credentials are valid, the OptionalPendingResult will be "done"
// and the GoogleSignInResult will be available instantly.
Log.d(TAG, " ---------------- CACHED SIGN-IN ------------");
System.out.println("pendingResult is done = ");
GoogleSignInResult signInResult = pendingResult.get();
onSilentLoginFinished(signInResult);
} else {
System.out.println("Setting result callback");
// If the user has not previously signed in on this device or the sign-in has expired,
// this asynchronous branch will attempt to sign in the user silently. Cross-device
// single sign-on will occur in this branch.
pendingResult.setResultCallback(new ResultCallback<GoogleSignInResult>() {
@Override
public void onResult(GoogleSignInResult googleSignInResult) {
System.out.println("googleSignInResult = " + googleSignInResult);
onSilentLoginFinished(googleSignInResult);
}
});
}
} else {
onSilentLoginFinished(null);
}
}
private void onSilentLoginFinished(GoogleSignInResult signInResult) {
System.out.println("GoogleLoginIdToken.onSilentLoginFinished");
if (signInResult != null) {
GoogleSignInAccount signInAccount = signInResult.getSignInAccount();
if (signInAccount != null) {
String emailAddress = signInAccount.getEmail();
String token = signInAccount.getIdToken();
System.out.println("token = " + token);
System.out.println("emailAddress = " + emailAddress);
}
}
}
}
Khi bạn nói mã thông báo, tôi có thể hỏi loại mã thông báo nào không? – zIronManBox
Mã thông báo mà tôi muốn từ Google API là mã thông báo ID (Tôi nghĩ đó là loại mã thông báo duy nhất mà bạn có thể nhận được bằng cách gọi GoogleSignInAccount.getIdToken()) –