Home > Blockchain >  Android Studio unable to run app on version 31 or above
Android Studio unable to run app on version 31 or above

Time:10-14

I have developed an android app that is working perfectly alright on android versions less than 31. For version 31 or greater I am getting the following error

Targeting S (version 31 and above) requires that one of FLAG_IMMUTABLE or FLAG_MUTABLE be specified when creating a PendingIntent. Strongly consider using FLAG_IMMUTABLE, only use FLAG_MUTABLE if some functionality depends on the PendingIntent being mutable, e.g. if it needs to be used with inline replies or bubbles.

Code

 public static void initSyncReceiver(Context context) {
    Intent intent = new Intent(context, SyncReciver.class);
    AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    boolean alarmUp = (PendingIntent.getBroadcast(context, 23231, intent, PendingIntent.FLAG_NO_CREATE) != null);
    if (!Common.SharedPreferenceHelper.getSharedPreference(context, context.getString(R.string.survey_sync_settings_key), true)) {
        if (alarmUp) {
            //alarm is up but not needed
            Log.e(TAG, "sync booking alarm is up but not needed, canceling..");
            PendingIntent pendingIntent = PendingIntent.getBroadcast(context,
                    23231, intent, PendingIntent.FLAG_CANCEL_CURRENT);
            pendingIntent.cancel();
            alarmManager.cancel(pendingIntent);
        } else {
            Log.e(TAG, "sync booking alarm neither up nor needed...");
        }
        return;
    }
    setAlarm(intent, context, 23231, 5);
    Log.e(TAG, "sync booking alarm needed so setting...");
}

I am getting the error on boolean alarmUp = (PendingIntent.getBroadcast(context, 23231, intent, PendingIntent.FLAG_NO_CREATE) != null);

I have already migrated to androidx. But no result.

Any help would be highly appreciated.

CodePudding user response:

If your app targets Android 12 or higher, you must specify the mutability of each PendingIntent object that your app creates.

Source: https://developer.android.com/guide/components/intents-filters#DeclareMutabilityPendingIntent

In short, add PendingIntent.FLAG_IMMUTABLE or PendingIntent.FLAG_MUTABLE to other PendingIntent flags.

Whether it's mutable or not depends. For alarms, it's normally immutable.

For example, before:

PendingIntent.FLAG_UPDATE_CURRENT

Now:

PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE

If you target Android 5 or lower, you need:

PendingIntent.FLAG_UPDATE_CURRENT or
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        PendingIntent.FLAG_IMMUTABLE
    } else {
        0
    }

P.S. I happened to read this commit today. It has a similar modification.

Updated code for the question:

 public static void initSyncReceiver(Context context) {
    Intent intent = new Intent(context, SyncReciver.class);
    AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
    boolean alarmUp = (PendingIntent.getBroadcast(context, 23231, intent, PendingIntent.FLAG_NO_CREATE | PendingIntent.FLAG_IMMUTABLE) != null);
    if (!Common.SharedPreferenceHelper.getSharedPreference(context, context.getString(R.string.survey_sync_settings_key), true)) {
        if (alarmUp) {
            //alarm is up but not needed
            Log.e(TAG, "sync booking alarm is up but not needed, canceling..");
            PendingIntent pendingIntent = PendingIntent.getBroadcast(context,
                    23231, intent, PendingIntent.FLAG_CANCEL_CURRENT | PendingIntent.FLAG_IMMUTABLE);
            pendingIntent.cancel();
            alarmManager.cancel(pendingIntent);
        } else {
            Log.e(TAG, "sync booking alarm neither up nor needed...");
        }
        return;
    }
    setAlarm(intent, context, 23231, 5);
    Log.e(TAG, "sync booking alarm needed so setting...");
}
  • Related