Our users have a chance to login, to authorize the app access to their Google Drive. We implement based on GoogleSignIn
and DriveClient
. (Not the yet another deprecated API GoogleApiClient
)
https://developers.google.com/drive/android/auth
After the users quit the app, we would like to Google Drive sync process still work seamlessly in background, without further user/UI interaction. (Able to handle case when login token is expired/invalid after few days/hours)
May I know how to achieve so. Any code example is appreciated.
silentSignIn
is the key to the solution. We also need to handle edge case, when silentSignIn
failed. Here's the real world code snippet.
public static GoogleSignInClient buildGoogleSignInClient() {
GoogleSignInOptions signInOptions =
new GoogleSignInOptions.Builder(GoogleSignInOptions.DEFAULT_SIGN_IN)
.requestScopes(Drive.SCOPE_APPFOLDER)
.build();
return GoogleSignIn.getClient(WeNoteApplication.instance(), signInOptions);
}
public static boolean silentSignInThenSync(SyncViewModel syncViewModel, boolean handleSignInRequired) {
GoogleSignInClient googleSignInClient = buildGoogleSignInClient();
Task<GoogleSignInAccount> task = googleSignInClient.silentSignIn();
if (task.isSuccessful()) {
syncViewModel.getSlientSignInSuccessLiveData().postValue(true);
return sync(task.getResult(), syncViewModel);
} else {
try {
Tasks.await(task);
try {
GoogleSignInAccount googleSignInAccount = task.getResult(ApiException.class);
syncViewModel.getSlientSignInSuccessLiveData().postValue(true);
return sync(googleSignInAccount, syncViewModel);
} catch (ApiException e) {
Log.e(TAG, "", e);
if (handleSignInRequired) {
if (e.getStatusCode() == GoogleSignInStatusCodes.SIGN_IN_REQUIRED) {
syncViewModel.getSignInRequiredLiveData().postValue(true);
return false;
}
}
String message = WeNoteApplication.instance().getString(R.string.sync_with_google_drive_failed_template, e.getLocalizedMessage());
syncViewModel.getMessageLiveData().postValue(message);
}
} catch (ExecutionException e) {
Log.e(TAG, "", e);
if (handleSignInRequired) {
if (e.getCause() instanceof ApiException) {
if (((ApiException) e.getCause()).getStatusCode() == GoogleSignInStatusCodes.SIGN_IN_REQUIRED) {
syncViewModel.getSignInRequiredLiveData().postValue(true);
return false;
}
}
}
String message = WeNoteApplication.instance().getString(R.string.sync_with_google_drive_failed_template, e.getLocalizedMessage());
syncViewModel.getMessageLiveData().postValue(message);
} catch (InterruptedException e) {
Log.e(TAG, "", e);
String message = WeNoteApplication.instance().getString(R.string.sync_with_google_drive_failed_template, e.getLocalizedMessage());
syncViewModel.getMessageLiveData().postValue(message);
}
}
return false;
}