Restreindre les interactions avec d'autres applications

Les autorisations ne concernent pas uniquement la demande de fonctionnalité système. Vous pouvez également limiter l'interaction d'autres applications avec les composants de votre application.

Ce guide explique comment vérifier l'ensemble des autorisations déclarées par une autre application. Il explique également comment configurer des activités, des services, des fournisseurs de contenu et des broadcast receivers afin de limiter l'interaction d'autres applications avec la vôtre.

Vérifier les autorisations d'une autre application

Pour consulter l'ensemble des autorisations déclarées par une autre application, utilisez un appareil ou un émulateur, puis procédez comme suit :

  1. Ouvrez l'écran Informations sur l'application.
  2. Sélectionnez Autorisations. L'écran Autorisations de l'application se charge.

    Cet écran présente un ensemble de groupes d'autorisations. Le système organise dans ces groupes l'ensemble des autorisations déclarées par une application.

Il existe plusieurs autres moyens utiles de vérifier les autorisations :

  • Lors d'un appel à un service, transmettez une chaîne d'autorisation à Context.checkCallingPermission(). Cette méthode renvoie un entier indiquant si cette autorisation a été accordée au processus d'appel en cours. Notez que cette méthode ne peut être utilisée que lorsque vous exécutez un appel provenant d'un autre processus, généralement via une interface IDL publiée à partir d'un service ou fournie d'une manière quelconque à un autre processus.
  • Pour vérifier si une autorisation particulière a été accordée à un autre processus, transmettez le processus (PID) à Context.checkPermission().
  • Pour vérifier si une autorisation particulière a été accordée à un autre package, transmettez le nom du package à PackageManager.checkPermission().

Limiter les interactions avec les activités de votre application

Utilisez l'attribut android:permission avec la balise <activity> dans le fichier manifeste afin de limiter les autres applications qui peuvent démarrer cette Activity. L'autorisation est vérifiée pendant Context.startActivity() et Activity.startActivityForResult(). Si l'appelant ne dispose pas de l'autorisation requise, une erreur SecurityException se produit.

Limiter les interactions avec les services de votre application

Utilisez l'attribut android:permission avec la balise <service> dans le fichier manifeste pour limiter les autres applications qui peuvent démarrer le Service associé ou s'y associer. L'autorisation est vérifiée pendant Context.startService(), Context.stopService() et Context.bindService(). Si l'appelant ne dispose pas de l'autorisation requise, une SecurityException se produit.

Limiter les interactions avec les fournisseurs de contenu de votre application

Utilisez l'attribut android:permission avec la balise <provider> pour limiter les autres applications qui peuvent accéder aux données d'un ContentProvider. Les fournisseurs de contenu ont accès à une fonctionnalité de sécurité supplémentaire appelée autorisations URI, décrite dans la section suivante. Contrairement aux autres composants, vous pouvez définir deux attributs d'autorisation distincts pour les fournisseurs de contenu : android:readPermission qui limite les autres applications ayant un accès en lecture à partir du fournisseur, et android:writePermission qui limite celles ayant un accès en écriture sur le fournisseur. Notez que si un fournisseur est protégé à la fois par une autorisation en lecture et en écriture, la seule autorisation en écriture ne permet pas à une application de lire des données à partir d'un fournisseur.

Les autorisations sont vérifiées la première fois que le fournisseur est récupéré et lorsqu'une application effectue des opérations au niveau de ce fournisseur. Si l'application à l'origine de la demande ne dispose d'aucune autorisation, une SecurityException se produit. L'utilisation de ContentResolver.query() nécessite l'autorisation de lecture. L'utilisation de ContentResolver.insert(), ContentResolver.update() ou ContentResolver.delete() requiert l'autorisation d'écriture. Dans tous ces cas, si l'autorisation requise n'a pas été accordée, une SecurityException est générée.

Autoriser l'accès par URI

Le système vous permet de contrôler précisément la manière dont les autres applications peuvent accéder aux fournisseurs de contenu de votre application. Votre fournisseur de contenu peut notamment se protéger avec des autorisations en lecture et en écriture, tout en permettant à ses clients directs de partager des URI spécifiques avec d'autres applications. Pour déclarer la compatibilité de votre application avec ce modèle, utilisez l'attribut android:grantUriPermissions ou l'élément <grant-uri-permission>.

Vous pouvez également accorder des autorisations pour chaque URI. Lorsqu'une activité est démarrée ou qu'un résultat est renvoyé à une activité, définissez l'indicateur d'intent Intent.FLAG_GRANT_READ_URI_PERMISSION, l'indicateur d'intent Intent.FLAG_GRANT_WRITE_URI_PERMISSION ou les deux. Cette configuration donne aux autres applications des autorisations en lecture, en écriture ou en lecture/écriture, respectivement, pour l'URI de données inclus dans l'intent. Les autres applications obtiennent ces autorisations pour cet URI spécifique, qu'elles soient ou non autorisées à accéder aux données du fournisseur de contenu de manière plus générale.

Supposons, par exemple, qu'un utilisateur utilise votre appli pour consulter un e-mail avec une image en pièce jointe. Les autres applications ne devraient pas pouvoir accéder au contenu de l'e-mail en général, mais peuvent avoir besoin de voir l'image. Votre application peut utiliser un intent et l'indicateur d'intent Intent.FLAG_GRANT_READ_URI_PERMISSION pour permettre aux applications appropriées de voir l'image.

La visibilité des applications est un autre point important à prendre en compte. Si votre application cible Android 11 (niveau d'API 30) ou version ultérieure, le système permet automatiquement à votre application de voir certaines applications et filtre les autres par défaut. Si votre application dispose d'un fournisseur de contenu et a accordé des autorisations d'URI à une autre application, elle est automatiquement visible par cette autre application.

Pour en savoir plus, consultez les supports de référence sur les méthodes grantUriPermission(), revokeUriPermission() et checkUriPermission().

Limiter les interactions avec les broadcast receivers de votre application

Utilisez l'attribut android:permission avec la balise <receiver> pour limiter les autres applications qui peuvent envoyer des annonces au BroadcastReceiver associé. L'autorisation est vérifiée après le renvoi de Context.sendBroadcast(), car le système tente de diffuser l'annonce envoyée au broadcast receiver donné. Cela signifie qu'un échec d'autorisation n'entraîne pas le renvoi d'une exception à l'appelant. C'est simplement que l'Intent n'est pas diffusé.

Dans un sens, vous pouvez accorder une autorisation à Context.registerReceiver() pour contrôler les autres applications qui peuvent diffuser des contenus à un broadcast receiver enregistré de façon programmatique. Dans l'autre sens, vous pouvez accorder une autorisation lors de l'appel de Context.sendBroadcast() pour limiter les broadcast receivers autorisés à recevoir la diffusion.

Notez qu'un broadcast receiver et qu'un diffuseur peuvent tous deux nécessiter une autorisation. Dans ce cas, les deux vérifications des autorisations doivent aboutir pour que l'intent soit transmis à la cible associée. Pour en savoir plus, consultez Limiter les diffusions avec des autorisations.