162
votes

Comment résoudre le "drapeau de mutabilité en attente manquante" Avertissement de peluche dans Android API 30+?

Dès que j'ai mis à jour la cible sdk à 30 + (Android r ou version ultérieure), un drapeau de mutabilité en attente de peluche sur mon en attente.flag_update_current Indicateur lorsque je veux définir en attente .

Comment dois-je gérer ce peluche sans effet sur la fonctionnalité de l'application?


1 commentaires

15 Réponses :


171
votes

Vous pouvez définir votre intention en attente comme

val updatedPendingIntent = PendingIntent.getActivity(
   applicationContext,
   NOTIFICATION_REQUEST_CODE,
   updatedIntent,
   PendingIntent.FLAG_IMMUTABLE or PendingIntent.FLAG_UPDATE_CURRENT // setting the mutability flag 
)


5 commentaires

Pour Android 21+: if (build.version.sdk_int> = build.version_codes.m) {en attente.flag_immutable ou en attente.flag_update_current} else {en attentent.flag_update_current}


Encore une fois, il s'agit d'une autre mauvaise décision de conception de Google. Au lieu de définir un comportement par défaut et d'enregistrer un avertissement, il écrase les applications ...


Merci pour cela, j'ai fait un fixer pour mon problème de dépendance


Cela fonctionne très bien à Kotlin


J'ai reçu la même erreur, en voyant diverses solutions, je définis les indicateurs de mutabilité comme celui-ci - `` `if (build.version.sdk_int> = build.version_codes.s) {En attentent = En attentent.getActivity (this, 0, intention, En attente.flag_immutable | en attente.flag_update_curre‌ nt); } else {En attentent = En attentent.getActivity (this, 0, intention, en attentent.flag_update_current); } ``



71
votes

Si vous n'utilisez pas la dernière version de WorkManager, vous verrez ce problème. Il a été corrigé dans la version 2.7.0-alpha02 :

rendre la mutabilité en attente explicite, pour réparer un crash lorsque vous ciblez Android 12

Gardez à l'esprit que 2.7.0-alpha02 n'est compatible qu'avec le SDK de prévisualisation du développeur Android 12. Vous pouvez donc attendre qu'il atteigne la bêta ou la RC.

mise à jour le 21 avril 2021 - ajoutant à cette réponse à toute personne sur Google le problème, le bug que vous pouvez rencontrer Peut ressembler à ceci:

 implementation 'androidx.work:work-runtime-ktx:2.7.0-alpha05'

Vous n'avez pas besoin d'être réellement directement en utilisant WorkManager dans votre application pour voir ce crash.

La solution, comme Décrit ici , c'est ajouter une dépendance à votre . Gradle Fichier pour Android 12 builds:

java.lang.IllegalArgumentException: com.myapp.myapp: Targeting S+ (version 10000 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.
        at android.app.PendingIntent.checkFlags(PendingIntent.java:386)
        at android.app.PendingIntent.getBroadcastAsUser(PendingIntent.java:657)
        at android.app.PendingIntent.getBroadcast(PendingIntent.java:644)
        at androidx.work.impl.utils.ForceStopRunnable.getPendingIntent(ForceStopRunnable.java:174)
        at androidx.work.impl.utils.ForceStopRunnable.isForceStopped(ForceStopRunnable.java:108)
        at androidx.work.impl.utils.ForceStopRunnable.run(ForceStopRunnable.java:86)
        at androidx.work.impl.utils.SerialExecutor$Task.run(SerialExecutor.java:75)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
        at java.lang.Thread.run(Thread.java:920)

Notez que cette dépendance est différente si vous utilisez Java unique etc. Assurez-vous donc de vérifier le dox ci-dessus.

Remplacez évidemment le numéro de version ci-dessus par les derniers. Et comme mentionné, il n'est pas compatible avec les builds pré-android-13.


9 commentaires

Y a-t-il des mises à jour à ce sujet? J'ai essayé cela en utilisant -Alpha04 et je réceptais toujours l'erreur. Je n'ai qu'une seule en attente pour ma demande et je ne peux pas aller de l'avant de cet accident. Les bibliothèques tierces peuvent-elles provoquer ce crash?


J'ai essayé avec implémentation "Androidx.work:work-runtime:2.7.0-alpha05" . Cela fonctionne bien avec Java.


Adam - Il est très probable que ce soit une autre bibliothèque qui provoque le crash. Vous pouvez voir l'arbre complet des dépendances de votre projet avec "./gradlew: app: dépendances" (dans Linux) par exemple, Play-Services-Ads-Lite: 20.2.0 dépend de AndroidX.Work:work-Runtime:2.1 0 / plate-forme / frameworks / support / + /… )


@Satheesh, oui - ils sont jusqu'à 2.7.0.beta-01 dans la source, mais il ne semble pas être disponible dans le référentiel pour générer encore des builts android.googlesource.com/platform .google.com / web / index.html? q = work-runtime # androidx.work: work-runtime-ktx "rel =" nofollow noreferrer "> maven.google.com/web/…


Je n'utilise pas de bibliothèque de travail et je ne l'ai pas à construire.gradle


C'est une mauvaise réponse, vous devez ajouter en attente.flag_immutable ou en attente.flag_update_current pour Android 12 comme répondu ici stackoverflow .com / A / 67046334/7767664


Ce n'est pas la mauvaise réponse, ce n'est peut-être pas la réponse complète. Si vous avez ce crash, mais que vous utilisez les indicateurs corrects dans votre en attente , c'est la solution dont vous avez besoin.


J'utilise un AndroidX.hilt: Hilt-Work: 1.0.0 Worker et ses accidents dans certains de l'appareil Samsung S20. Une solution pour moi?


C'est tellement idiot. Je souhaite annuler des alarmes plus anciennes sur le périphérique de l'utilisateur après une mise à jour, j'ai donc besoin de recréer l'ancien Entendant exact avec FLAG_UPDATE_CURRENT . Mais maintenant, il s'écrase juste en créant l'objet, donc je n'ai aucun moyen de le faire sur des appareils plus récents 🤦‍️



3
votes

C'est un problème avec la bibliothèque de travail. Même la dernière version est affectée 2.7.0-alpha04

https://issuetracker.google.com/issues/194108978

En tant que solution de contournement temporaire - commentez y compris la dépendance "travail" dans Gradle et supprimez en utilisant cette classe via le projet. Au moins de cette manière, vous pouvez exécuter l'application normalement et travailler sur d'autres fonctionnalités et zones ....


0 commentaires

9
votes

Si vous utilisez Java et Adob, vous ressentez l'erreur en attente du SDK SDK ou Android 12. Voici un correctif pour qu'Adob utilise le bon travail-runtime.

implementation 'com.google.android.gms:play-services-ads:19.5.0'
    constraints {
        implementation('androidx.work:work-runtime:2.7.0-alpha05') {
            because 'previous versions have a bug impacting this application'
        }
    }


1 commentaires

Ceci est corrigé depuis que la version play-service-ADS: 20.4.0 comme le dit les notes de publication Developers.google.com/admob/android/rel-notes



10
votes

Dans mon cas, il a également été par des bibliothèques tierces qui utilisaient les anciennes versions de WorkManager, pour forcer la nouvelle version de travail Android sur toutes les dépendances utilisent ceci dans votre root build.gradle fichier:

allproject {
  project.configurations.all {
    resolutionStrategy {
      force 'androidx.work:work-runtime:2.7.0'
    }
  }
}


0 commentaires

54
votes

Si vous laissez votre application s'exécuter dans Android 12, il existe un nouveau drapeau de mutabilité en attente. Si vous ne voulez pas que votre entente soit mutée, utilisez

//Work Manager dependency
implementation 'androidx.work:work-runtime:2.7.1'

Si vous voulez que votre entente soit mutée, utilisez les éléments suivants:

PendingIntent pendingIntent;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
        pendingIntent = PendingIntent.getActivity(this,
                0, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_MUTABLE);

    }else {
        pendingIntent = PendingIntent.getActivity(this,
                0, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT);

    }


5 commentaires

Ne devrait-il pas être la version S au lieu de m?


Pour le drapeau_mutable oui, il devrait être s car il a été ajouté dans SDK 31, Flag_inmutable a été ajouté dans le SDK 23, donc m est ok


Merci pour cela, résout mon exigence Flag_mutable sur une intention qui charge une URL dynamiquement à partir d'une liste dans un widget.


Il doit être sûr d'utiliser les drapeaux les plus récents sur les niveaux d'API plus anciens car la valeur est inclinée. Un drapeau qui n'est pas connu à l'ancien niveau, ne devrait pas interférer avec sa vérification bit dans les drapeaux qu'il connaît.


À moins que je ne devienne fou, cela se traduit par un "drapeau de mutabilité en attente manquant" Linter Avertissement dans le bloc else . Nous pouvons @SuppressLint ("non spécifié-ImmutableFlag") mais il semble que le linter devrait être conscient de la branche de code, non? Existe-t-il une meilleure solution pour réparer cet avertissement?



5
votes

Ce crash est résolu avec: implémentation 'Androidx.work:work-runtime:2.7.1'


0 commentaires

0
votes

J'ai mis à jour ma version work-runtime-ktx vers 2.7.1

Après le changement ci-dessus, j'ai eu une autre erreur

java.lang.IllegalStateException: SimpleTypeImpl should not be created for error type: ErrorScope{Error scope for class <ERROR CLASS> with arguments: org.jetbrains.kotlin.types.IndexedParametersSubstitution@14ac19e7}

Regardez comment j'ai résolu l'erreur ci-dessus en mettant à jour kotlin-gradle-plugin version ici .


0 commentaires

2
votes

Comme j'avais quatre en attentes différents dans mon code, j'ai commencé par ajouter Flag_immutable à chacun d'eux. Cependant, le problème est resté. Après avoir passé beaucoup de temps à analyser mes 4 intentions, il m'est apparu que le problème pourrait provenir de l'une de mes bibliothèques.

Dans Build.gradle, les bibliothèques sont normalement mises en évidence lorsqu'elles sont anciennes, mais ce n'est pas le cas pour la base de feu Bom.

J'avais:

implementation platform('com.google.firebase:firebase-bom:29.0.4')

Il s'est avéré que c'était très ancien. Après la mise à jour de

implementation platform('com.google.firebase:firebase-bom:26.1.1')

tout était bien. Plus d'erreurs Flag_immutable


0 commentaires

14
votes

Si votre application cible Android 12 (Targetsdkversion = 31) , et utilise une ancienne version du développeur workManager directement ou par l'une des bibliothèques tierces alors vous devez alors Mettez-le à la dernière pour le résoudre.

dependencies {
    val work_version = "2.7.1"

    // (Java only)
    implementation("androidx.work:work-runtime:$work_version")

    // Kotlin + coroutines
    implementation("androidx.work:work-runtime-ktx:$work_version")

    // optional - RxJava2 support
    implementation("androidx.work:work-rxjava2:$work_version")        
}


0 commentaires

5
votes
final int flag =  Build.VERSION.SDK_INT >= Build.VERSION_CODES.M ? PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE : PendingIntent.FLAG_UPDATE_CURRENT;
PendingIntent pendingIntent = PendingIntent.getActivity(context, PENDING_INTENT_REQUEST_CODE, notificationIntent, flag);

0 commentaires

3
votes

J'ai eu des accidents comme Exception fatale: java.lang.illegalargumentException. Non posté. En attente des actions avec des entrées distantes doit être mutable .

J'ai écrit cette méthode ULIL, qui permet d'envoyer mutabilité en tant que param. Parfois, il est nécessaire d'obtenir des drapeaux mutables, par exemple pour Actions de réponse dans les notifications.

val quickReplyPendingIntent = PendingIntent.getBroadcast(
                context, notificationId, replyIntent,
                getPendingIntentFlags(true)
            )


0 commentaires

5
votes

Si vous laissez votre application s'exécuter dans Android 12, il existe un nouveau drapeau de mutabilité en attente. Si vous ne voulez pas que votre en attente en attente soit muette, utilisez

java

//Work Manager dependency
implementation 'androidx.work:work-runtime:2.7.1'

kotlin

val updatedPendingIntent = PendingIntent.getActivity(
   applicationContext,
   NOTIFICATION_REQUEST_CODE,
   updatedIntent,
   PendingIntent.FLAG_MUTABLE or PendingIntent.FLAG_UPDATE_CURRENT // setting the mutability flag 
)

si vous Je veux que votre en attente soit muet Utilisez les éléments suivants:

java

PendingIntent updatedPendingIntent = PendingIntent.getActivity(
   applicationContext,
   NOTIFICATION_REQUEST_CODE,
   updatedIntent,
   PendingIntent.FLAG_MUTABLE | PendingIntent.FLAG_UPDATE_CURRENT // setting the mutability flag 
)

kotlin

val updatedPendingIntent = PendingIntent.getActivity(
   applicationContext,
   NOTIFICATION_REQUEST_CODE,
   updatedIntent,
   PendingIntent.FLAG_IMMUTABLE or PendingIntent.FLAG_UPDATE_CURRENT // setting the mutability flag 
)

à La dernière implémentation de cette dépendance

PendingIntent updatedPendingIntent = PendingIntent.getActivity(
   applicationContext,
   NOTIFICATION_REQUEST_CODE,
   updatedIntent,
   PendingIntent.FLAG_IMMUTABLE | PendingIntent.FLAG_UPDATE_CURRENT // setting the mutability flag 
)


0 commentaires

1
votes

Dans mon projet, cette ligne a fonctionné

En attente deintent en attente = en attente.getActivity (this, 0, notificationIntent, en attentent.flag_update_current |


0 commentaires

0
votes

Ce problème survient lorsque vous améliorez votre projet et cibler Android version 12, Android Run App sur Android 12. La solution est utilisée, vous pouvez mettre à jour votre stagiaire en attente

Cibler S + (version 31 et supérieure) nécessite que l'un de Flag_immutable ou flag_mutable être spécifié lors de la création d'un Entrez une description de l'image ici

Utilisé ci-dessous Code

//Work Manager dependency
implementation 'androidx.work:work-runtime:2.7.1'

et implémentez également ce travail de dépendance si vous utilisez un récepteur dans Votre projet

 PendingIntent pendingIntent = null;
        if (Build.VERSION.SDK_INT>= Build.VERSION_CODES.S){
             pendingIntent = stackBuilder.getPendingIntent(1, PendingIntent.FLAG_MUTABLE);

        }else {
             pendingIntent = stackBuilder.getPendingIntent(1, PendingIntent.FLAG_UPDATE_CURRENT);

        }


0 commentaires