Comment demander des autorisations à un service dans Android Marshmallow

101

Dans Android Marshmallow, les autorisations doivent être demandées au moment de l'exécution lorsqu'elles sont nécessaires, au lieu de toutes en même temps lorsqu'une application est installée. Cependant, je ne peux que sembler demander des autorisations à une activité, ce qui pose un problème car mon application ne contient que des services. (Pourquoi, demandez-vous? L'application contient un cadran de montre Android Wear intégré, et le téléphone ne fait que rechercher des photos à proximité pour les envoyer à la montre. Aucune activité n'est nécessaire. Mais il nécessite des autorisations de localisation.)

Alors, existe-t-il un moyen de demander des autorisations à un service? Ou forcer en quelque sorte les autorisations à être accordées au moment de l'installation comme par le passé?

Tony Wickham
la source
ce problème également à l'intérieur de la classe Application
itzhar
Essayez ceci, il peut s'agir de travail stackoverflow.com/a/41221852/5488468
Bipin Bharti
Ma bibliothèque permet de gérer facilement les autorisations d'exécution à partir de n'importe quel contexte et gère également "Ne plus demander". github.com/nabinbhandari/Android-Permissions
Nabin Bhandari

Réponses:

47

requestPermission()ne peut être appelé qu'à partir d'un Activityet non d'un Service(contrairement à ce checkPermission()qui ne nécessite que PackageManager). Vous devez donc faire un travail supplémentaire pour contourner cela; vous devez fournir un Activitydans votre application et, par exemple, vous Servicepouvez vérifier les autorisations dont il a besoin et si elles n'ont pas encore été accordées, il peut créer une notification et qui peut informer l'utilisateur avec un court message descriptif des raisons pour lesquelles il y a une notification et ce qui doit se passer lorsqu'ils cliquent sur la notification, etc.

Ali Naddaf
la source
C'est la solution proposée par Benjamin Poiesz . Vous pouvez écouter ce podcast de 23h40
Xiaomi
Vous pouvez également appeler requestPermission () à l'intérieur de fragment.
Misagh Emamverdi
3
Quelle est la solution dans le cas d'un service d'arrière-plan en cours d'exécution vérifiant périodiquement les mises à jour de localisation et je désactive simplement l'autorisation de localisation dans les paramètres. Puisqu'il n'y a aucune activité, cela provoque le blocage de mon service lorsque je rouvre l'application
stud91
1
@ stud91 À tout le moins, détectez les exceptions de sécurité ou interrogez les autorisations chaque fois que vous demandez des mises à jour de localisation. Cela empêchera votre application de planter (bien que vous n'obtiendrez aucun emplacement si l'autorisation a été révoquée). Mieux encore: vérifiez l'autorisation, et si elle est manquante, affichez une notification qui amène l'utilisateur à une activité qui n'est qu'un espace réservé pour la boîte de dialogue des autorisations.
user149408
8
Voici comment je l'ai résolu: github.com/mvglasow/satstat/blob/master/src/com/vonglasow / ... Il peut être appelé depuis n'importe quel Contextqui implémente également OnRequestPermissionsResultCallback. La fonctionnalité est similaire à la norme requestPermission().
user149408
15

Je suis d'accord, c'est très gênant pour les services, je pense que vous devriez signaler un problème sur la page d'Android Developer Preview pour cela.

Pour le moment, je pense que la meilleure solution est de vérifier l'autorisation sur le service et d'afficher une notification si l'autorisation est manquante. Mieux encore, créez un DialogActivity pour demander l'autorisation lorsque les utilisateurs appuient sur la notification.

Derek Fung
la source
7

Jetez un œil à la bibliothèque PermissionEverywhere . Il vous permet de demander l'autorisation de n'importe quel contexte.

Il crée une notification en cliquant sur laquelle il ouvre une activité demandant une autorisation.

Exemple de code de la page github de la bibliothèque: -

@Override
  protected Boolean doInBackground(Void... params) {
      PermissionResponse response = PermissionEverywhere.getPermission(getApplicationContext(), 
      new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE},
              REQ_CODE,
              "Notification title", 
              "This app needs  a write permission", 
              R.mipmap.ic_launcher)
              .call();
      //waits..
      boolean isGranted = response.isGranted();

      if(isGranted){ //changed from isGrante to isGranted
      // Do stuff
      }
  }
Heisenberg
la source
1
J'ai essayé la version asynchrone dans un service et cela n'a pas fonctionné. onComplete n'a jamais été appelé
Leo Droidcoder
Bonne idée, mais ce n'est pas disponible dans le référentiel
naXa
2
Ce package a fonctionné pour moi, merci pour la suggestion. Je noterais cependant que je n'ai pas essayé la version asynchrone. De plus, pour ceux qui rencontrent des problèmes lors de l'utilisation PermissionEverywhere, assurez-vous que vous déclarez l'activité d'assistance dans votre manifeste ET assurez-vous que lorsque vous la déclarez, elle est liée au package correct (si vous utilisez PermissionEverywherecomme package séparé). Il m'a fallu beaucoup de temps pour réaliser que je ne spécifiais pas réellement le PermissionEverywherepackage dans le manifeste.
user3570982
J'ai lancé PermissionEverywherel'application de démonstration et cela n'a pas fonctionné.
Ixx
2

Il existe une bibliothèque très simple qui permet de faire exactement cela. Vous pouvez vérifier les autorisations de n'importe où (même à partir d'un service), selon que l'application est au premier plan ou en arrière-plan, elle affiche une boîte de dialogue normale ou génère une notification demandant des autorisations. Le code est vraiment facile à comprendre et il est également très facile à utiliser.

Essayez-le: autorisations Android

Nishkarsh
la source
-2

Vous pouvez utiliser ResultReceiverpour créer un récepteur de la réponse des utilisateurs, puis le transmettre comme rappel à l'activité, via les notifications PendingIntent. Référence

Farrux Bahodirov
la source