Google+ sign-in error: statusCode = SIGN_IN_REQUIRED on Android 4

My goal is to develop a game that allows you to try out music with friends. You can test it yourself by signing up for this Google+ community: https://plus.google.com/u/0/communities/100815426127955231967

I am testing my application on several devices:

  • Motorola Xoom, android 4.1.2, build JZO54K
  • Nexus 7 2012 Wifi "nagasi", android 5.0.2, build LRX22G
  • Nexus 5, android 5.0.1, build LRX22C

I use the same Google user on all devices. My application is registered and I have included the correct lines in the manifest file.

With the exact same code, I can successfully connect to the Google Plus and Games services on Lollipop Nexus 7 and Nexus 5 devices, but not on the Xoom android 4 device.

Here is the code, the connection request is in Activity onCreate:

@Override protected void onCreate(Bundle savedInstanceState) { if (GooglePlayServicesUtil.isGooglePlayServicesAvailable(this) == ConnectionResult.SUCCESS) { if (mGoogleApiClient == null) { Plus.PlusOptions plusOptions = new Plus.PlusOptions.Builder().addActivityTypes( "http://schemas.google.com/AddActivity", "http://schemas.google.com/ReviewActivity").build(); mGoogleApiClient = new GoogleApiClient.Builder(this).addApi(Games.API).addScope(Games.SCOPE_GAMES) .addApi(Plus.API, plusOptions).addScope(Plus.SCOPE_PLUS_LOGIN) .addConnectionCallbacks(this).addOnConnectionFailedListener(this).build(); } mGoogleApiClient.connect(); } else { Toast.makeText(this, R.string.texteErreurGPlus, Toast.LENGTH_LONG).show(); } } 

For an Android 4 device, the onConnectionFailed callback is called with the message:

 GoogleApiClient connection failed: ConnectionResult{statusCode=SIGN_IN_REQUIRED, resolution=PendingIntent{412f07c8: android.os.BinderProxy@413b0bd0 }} : @Override public void onConnectionFailed(ConnectionResult result) { if (mResolvingConnectionFailure) { // Already resolving return; } else if (result.hasResolution()) { try { mResolvingConnectionFailure = true; result.startResolutionForResult(this, REQUEST_CODE_RESOLUTION); } catch (SendIntentException e) { // There was an error with the resolution intent. Try again. mGoogleApiClient.connect(); } } else { // Show dialog using GooglePlayServicesUtil.getErrorDialog() showErrorDialog(result.getErrorCode()); mResolvingConnectionFailure = true; } } 

This results in onActivityResult activity:

 @Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); switch (requestCode) { case REQUEST_CODE_RESOLUTION: mResolvingConnectionFailure = false; if (resultCode == RESULT_OK) { // Make sure the app is not already connected or attempting to connect if (!mGoogleApiClient.isConnecting() && !mGoogleApiClient.isConnected()) { mGoogleApiClient.connect(); } } else { mGoogleApiClient.connect(); } break; 

and an infinite loop, because resultCode is not equal to RESULT_OK.

Here is the gradle file for Android Studio:

 apply plugin: 'android' android { compileSdkVersion 21 buildToolsVersion '21.1.2' defaultConfig { applicationId "debut.blindtest" minSdkVersion 16 targetSdkVersion 21 compileOptions { sourceCompatibility JavaVersion.VERSION_1_7 targetCompatibility JavaVersion.VERSION_1_7 } } buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.txt' } } } dependencies { compile project(':volley') compile 'com.android.support:appcompat-v7:21.0.2' compile 'com.google.android.gms:play-services-plus:6.5.+' compile 'com.google.android.gms:play-services-games:6.5.+' compile files('libs/deezer-sdk-0.10.16.jar') } 

Thread of execution:

  • The main onCreate activity referenced by the GoogleApiClient connection
  • The main activity of onConnectionFailed is called, the result has permission, so result.startResolutionForResult is called
  • The main activity of onActivityResult is called

An exception:

 01-07 22:38:01.260 4894-4894/debut.blindtest I/TagApplicationBlindTest﹕ onActivityResult : REQUEST_CODE_RESOLUTION : resultCode : 0 01-07 22:38:01.280 4935-4936/? D/dalvikvm﹕ GC_CONCURRENT freed 448K, 7% free 6800K/7303K, paused 24ms+3ms, total 55ms 01-07 22:38:01.280 4935-4935/? D/dalvikvm﹕ WAIT_FOR_CONCURRENT_GC blocked 22ms 01-07 22:38:01.280 4894-4894/debut.blindtest E/BaseGamesUtils﹕ No standard error dialog available. Making fallback dialog. 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to find class referenced in signature (Landroid/app/SharedElementCallback;) 01-07 22:38:01.380 4864-4864/? I/dalvikvm﹕ Could not find method android.app.Activity.setEnterSharedElementCallback, referenced from method android.support.v4.app.q.setEnterSharedElementCallback 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to resolve virtual method 80: Landroid/app/Activity;.setEnterSharedElementCallback (Landroid/app/SharedElementCallback;)V 01-07 22:38:01.380 4864-4864/? D/dalvikvm﹕ VFY: replacing opcode 0x6e at 0x000e 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to find class referenced in signature (Landroid/app/SharedElementCallback;) 01-07 22:38:01.380 4864-4864/? I/dalvikvm﹕ Could not find method android.app.Activity.setExitSharedElementCallback, referenced from method android.support.v4.app.q.setExitSharedElementCallback 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to resolve virtual method 81: Landroid/app/Activity;.setExitSharedElementCallback (Landroid/app/SharedElementCallback;)V 01-07 22:38:01.380 4864-4864/? D/dalvikvm﹕ VFY: replacing opcode 0x6e at 0x000e 01-07 22:38:01.380 4864-4864/? I/dalvikvm﹕ Could not find method android.app.Activity.finishAfterTransition, referenced from method android.support.v4.app.q.supportFinishAfterTransition 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to resolve virtual method 46: Landroid/app/Activity;.finishAfterTransition ()V 01-07 22:38:01.380 4864-4864/? D/dalvikvm﹕ VFY: replacing opcode 0x6e at 0x0006 01-07 22:38:01.380 4864-4864/? I/dalvikvm﹕ Could not find method android.app.Activity.postponeEnterTransition, referenced from method android.support.v4.app.q.supportPostponeEnterTransition 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to resolve virtual method 77: Landroid/app/Activity;.postponeEnterTransition ()V 01-07 22:38:01.380 4864-4864/? D/dalvikvm﹕ VFY: replacing opcode 0x6e at 0x0006 01-07 22:38:01.380 4864-4864/? I/dalvikvm﹕ Could not find method android.app.Activity.startPostponedEnterTransition, referenced from method android.support.v4.app.q.supportStartPostponedEnterTransition 01-07 22:38:01.380 4864-4864/? W/dalvikvm﹕ VFY: unable to resolve virtual method 89: Landroid/app/Activity;.startPostponedEnterTransition ()V 01-07 22:38:01.380 4864-4864/? D/dalvikvm﹕ VFY: replacing opcode 0x6e at 0x0006 01-07 22:38:01.410 4894-4898/debut.blindtest D/dalvikvm﹕ GC_CONCURRENT freed 325K, 6% free 7193K/7623K, paused 14ms+38ms, total 115ms 01-07 22:38:01.410 4935-4936/? D/dalvikvm﹕ GC_CONCURRENT freed 460K, 8% free 6851K/7367K, paused 19ms+12ms, total 83ms 01-07 22:38:01.410 4935-4935/? D/dalvikvm﹕ WAIT_FOR_CONCURRENT_GC blocked 41ms 01-07 22:38:01.450 4864-4864/? E/dalvikvm﹕ Could not find class 'android.app.AppOpsManager', referenced from method com.google.android.gms.common.util.ea 01-07 22:38:01.450 4864-4864/? W/dalvikvm﹕ VFY: unable to resolve check-cast 35 (Landroid/app/AppOpsManager;) in Lcom/google/android/gms/common/util/e; 01-07 22:38:01.450 4864-4864/? D/dalvikvm﹕ VFY: replacing opcode 0x1f at 0x0010 01-07 22:38:01.460 4864-4864/? E/SignInActivity﹕ SignInActivity must be started with startActivityForResult 01-07 22:38:01.530 4935-4936/? D/dalvikvm﹕ GC_CONCURRENT freed 457K, 7% free 6916K/7431K, paused 18ms+5ms, total 61ms 

Could you help me find out what I have to do to be compatible with Android 4 devices?

+4
android google-plus
source share
3 answers

With automatic connection in onConnectionFailed() you will try to connect as many times as necessary until you get a valid connection as you feel it. This means that even if users do not want to log in (for example, they canceled the cancellation in the login dialog box), they will be constantly requested again and again.

Instead, the Google+ Sign In Guide uses the mSignInClicked variable, which helps determine if onConnectionFailed() should connect immediately (ideal situation for an unrelated person calling onConnectionFailed() , but you haven't called startResolutionForResult() yet - just save ConnectionResult while the user will not go).

If you want to keep the initial attempt to automatically log in, you can consider the approach used in the sample Google Play game services as TrivialQuest , where their onConnnectionFailed() method looks like this:

 public void onConnectionFailed(ConnectionResult connectionResult) { Log.d(TAG, "onConnectionFailed() called, result: " + connectionResult); if (mResolvingConnectionFailure) { Log.d(TAG, "onConnectionFailed() ignoring connection failure; already resolving."); return; } if (mSignInClicked || mAutoStartSignInFlow) { mAutoStartSignInFlow = false; mSignInClicked = false; mResolvingConnectionFailure = BaseGameUtils.resolveConnectionFailure(this, mGoogleApiClient, connectionResult, RC_SIGN_IN, getString(R.string.signin_other_error)); } showSignInBar(); } 

Where they use BaseGameUtils helper methods to simplify connection to Google services (note: nothing is a particularly game service linked in there - it works equally well with all GoogleApiClient connections).

+1
source share

I deleted the line "android: launchMode =" singleInstance "in my manifest file. After several build / launch cycles, it started working. I just need to redesign my application to change my actions.

+1
source share

make sure you have permissions:

 <uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> <uses-permission android:name="android.permission.GET_ACCOUNTS" /> 
0
source share

All Articles