Home | History | Annotate | Download | only in articles
      1 page.title=Best Practices for App Permissions
      2 page.metaDescription=How to manage permissions to give users context and control.
      3 page.tags=permissions, user data
      4 meta.tags="permissions", "user data"
      5 page.image=images/cards/card-user-permissions_2x.png
      6 
      7 page.article=true
      8 @jd:body
      9 
     10 <div id="tb-wrapper">
     11 <div id="tb">
     12     <h2>In this document</h2>
     13     <ol>
     14       <li><a href="#tenets_of_working_with_android_permissions">Tenets</a></li>
     15       <li><a href="#version_specific_details_permissions_in_m">Permissions in Android
     16       6.0+</h2></a></li>
     17       <li><a href="#avoid_requesting_unnecessary_permissions">Avoid Requesting
     18 Unnecessary Permissions</h2></a>
     19       <ol>
     20         <li><a href="#a_camera_contact_access_with_real-time_user_requests">Camera/Contact
     21         access with realtime user requests</a></li>
     22         <li><a href="#b_running_in_the_background_after_losing_audio_focus">Running in
     23 the background after losing audio focus</a></li>
     24         <li><a href="#c_determine_the_device_your_instance_is_running_on">Determine the
     25 device your instance is running on</a></li>
     26         <li><a href="#d_create_a_unique_identifier_for_advertising_or_user_analytics">
     27 Create a unique identifier for advertising or user analytics</a></li>
     28       </ol>
     29       </li>
     30       <li><a href="#know_the_libraries_you're_working_with">Know the Libraries You're
     31 Working With</a></li>
     32       <li><a href="#be_transparent">Be Transparent</a></li>
     33     </ol>
     34     <h2>You should also read</h2>
     35     <ol>
     36       <li><a href="{@docRoot}guide/topics/security/permissions.html">System Permissions</a></li>
     37       <li><a href="{@docRoot}training/permissions/index.html">Working with System
     38       Permissions</a></li>
     39     </ol>
     40   </div>
     41 </div>
     42 
     43 <p>
     44   Permission requests protect sensitive information available from a device and
     45   should only be used when access to information is necessary for the
     46   functioning of your app. This document provides tips on ways you might be
     47   able to achieve the same (or better) functionality without requiring access
     48   to such information; it is not an exhaustive discussion of how permissions
     49   work in the Android operating system.
     50 </p>
     51 
     52 <p>
     53   For a more general look at Android permissions, please see <a href=
     54   "{@docRoot}training/articles/user-data-overview.html">Permissions
     55   and User Data</a>. For details on how to work with permissions in your code,
     56   see <a href="{@docRoot}training/permissions/index.html">Working with System Permissions</a>.
     57   For best practices for working with unique identifiers, please see <a href=
     58   "{@docRoot}training/articles/user-data-ids.html">Best Practices for
     59   Unique Identifiers</a>. 
     60 </p>
     61 
     62 <h2 id="tenets_of_working_with_android_permissions">Tenets of Working
     63 with Android Permissions</h2>
     64 
     65 <p>
     66   We recommend following these tenets when working with Android permissions:
     67 </p>
     68 
     69 <p>
     70   <em><strong>#1: Only use the permissions necessary for your app to
     71   work</strong></em>. Depending on how you are using the permissions, there may
     72   be another way to do what you need (system intents, identifiers,
     73   backgrounding for phone calls) without relying on access to sensitive
     74   information.
     75 </p>
     76 
     77 <p>
     78   <em><strong>#2: Pay attention to permissions required by
     79   libraries.</strong></em> When you include a library, you also inherit its
     80   permission requirements. You should be aware of what you're including, the
     81   permissions they require, and what those permissions are used for.
     82 </p>
     83 
     84 <p>
     85   <em><strong>#3: Be transparent.</strong></em> When you make a permissions
     86   request, be clear about what youre accessing, and why, so users can make
     87   informed decisions. Make this information available alongside the permission
     88   request including install, runtime, or update permission dialogues.
     89 </p>
     90 
     91 <p>
     92   <em><strong>#4: Make system accesses explicit.</strong></em> Providing
     93   continuous indications when you access sensitive capabilities (for example, the
     94   camera or microphone) makes it clear to users when youre collecting data and
     95   avoids the perception that you're collecting data surreptitiously.
     96 </p>
     97 
     98 <p>
     99   The remaining sections of this guide elaborate on these rules in the context
    100   of developing Android applications.
    101 </p>
    102 
    103 <h2 id="version_specific_details_permissions_in_m">Permissions in Android 6.0+</h2>
    104 
    105 <p>
    106   Android 6.0 Marshmallow introduced a <a href=
    107   "{@docRoot}training/permissions/requesting.html">new permissions model</a> that
    108   lets apps request permissions from the user at runtime, rather than prior to
    109   installation. Apps that support the new model request permissions when the app
    110   actually requires the services or data protected by the services. While this
    111   doesn't (necessarily) change overall app behavior, it does create a few
    112   changes relevant to the way sensitive user data is handled:
    113 </p>
    114 
    115 <p>
    116   <em><strong>Increased situational context</strong></em>: Users are
    117   prompted at runtime, in the context of your app, for permission to access the
    118   functionality covered by those permission groups. Users are more sensitive to
    119   the context in which the permission is requested, and if theres a mismatch
    120   between what you are requesting and the purpose of your app, it's even
    121   more important to provide detailed explanation to the user as to why youre
    122   requesting the permission; whenever possible, you should provide an
    123   explanation of your request both at the time of the request and in a
    124   follow-up dialog if the user denies the request.
    125 </p>
    126 
    127 <p>
    128   <em><strong>Greater flexibility in granting permissions</strong></em>: Users
    129   can deny access to individual permissions at the time theyre requested
    130   <em>and</em> in settings, but they may still be surprised when functionality is
    131   broken as a result. Its a good idea to monitor how many users are denying
    132   permissions (e.g. using Google Analytics) so that you can either refactor
    133   your app to avoid depending on that permission or provide a better
    134   explanation of why you need the permission for your app to work properly. You
    135   should also make sure that your app handles exceptions created when users
    136   deny permission requests or toggle off permissions in settings.
    137 </p>
    138 
    139 <p>
    140   <em><strong>Increased transactional burden</strong></em>: Users will be asked
    141   to grant access for permission groups individually and not as a set. This
    142   makes it extremely important to minimize the number of permissions youre
    143   requesting because it increases the user burden for granting permissions and
    144   increases the probability that at least one of the requests will be denied.
    145 </p>
    146 
    147 <h2 id="avoid_requesting_unnecessary_permissions">Avoid Requesting
    148 Unnecessary Permissions</h2>
    149 
    150 <p>
    151   This section provides alternatives to common use-cases that will help you
    152   limit the number of permission requests you make. Since the number and type
    153   of user-surfaced permissions requested affects downloads compared to other
    154   similar apps requesting fewer permissions, its best to avoid requesting
    155   permissions for unnecessary functionality.
    156 </p>
    157 
    158 <h3 id="a_camera_contact_access_with_real-time_user_requests">Camera/contact
    159 access with realtime user requests</h3>
    160 
    161 <p>
    162   <em>In this case, you need occasional access to the device's camera or
    163   contact information and dont mind the user being asked every time you need
    164   access.</em>
    165 </p>
    166 
    167 <p>
    168   If your requirement for access to user data is infrequent &mdash; in other
    169   words, it's not unacceptably disruptive for the user to be presented with a
    170   runtime dialogue each time you need to access data &mdash; you can use an
    171   <em>intent based request</em>. Android provides some system intents that
    172   applications can use without requiring permissions because the user chooses
    173   what, if anything, to share with the app at the time the intent based request
    174   is issued.
    175 </p>
    176 
    177 <p>
    178   For example, an intent action type of <code><a href=
    179   "{@docRoot}reference/android/provider/MediaStore.html#ACTION_IMAGE_CAPTURE">MediaStore.ACTION_IMAGE_CAPTURE</a></code>
    180   or <code><a href=
    181   "{@docRoot}reference/android/provider/MediaStore.html#ACTION_VIDEO_CAPTURE">MediaStore.ACTION_VIDEO_CAPTURE</a></code>
    182   can be used to capture images or videos without directly using the <a href=
    183   "{@docRoot}reference/android/hardware/Camera.html">Camera</a> object (or
    184   requiring the permission). In this case, the system intent will ask for the
    185   users permission on your behalf every time an image is captured.
    186 </p>
    187 
    188 <h3 id="b_running_in_the_background_after_losing_audio_focus">Running in
    189 the background after losing audio focus</h3>
    190 
    191 <p>
    192   <em>In this case, your application needs to go into the background when the
    193   user gets a phone call and refocus only once the call stops.</em>
    194 </p>
    195 
    196 <p>
    197   The common approach in these cases - for example, a media player muting or
    198   pausing during a phone call - is to listen for changes in the call state
    199   using <code>PhoneStateListener</code> or listening for the broadcast of
    200   <code>android.intent.action.PHONE_STATE</code>. The problem with this
    201   solution is that it requires the <code>READ_PHONE_STATE</code> permission,
    202   which forces the user to grant access to a wide cross section of sensitive
    203   data such as their device and SIM hardware IDs and the phone number of the
    204   incoming call.
    205 </p>
    206 
    207 <p>
    208   You can avoid this by requesting <code>AudioFocus</code> for your app, which
    209   doesn't require explicit permissions (because it does not access sensitive
    210   information). Simply put the code required to background your audio in the
    211   <code><a href=
    212   "{@docRoot}reference/android/media/AudioManager.OnAudioFocusChangeListener.html#onAudioFocusChange(int)">
    213   onAudioFocusChange()</a></code> event handler and it will run automatically
    214   when the OS shifts its audio focus. More detailed documentation on how to do
    215   this can be found <a href=
    216   "{@docRoot}training/managing-audio/audio-focus.html">here</a>.
    217 </p>
    218 
    219 <h3 id="c_determine_the_device_your_instance_is_running_on">Determine the
    220 device your instance is running on</h3>
    221 
    222 <p>
    223   <em>In this case, you need a unique identifier to determine which device the
    224   instance of your app is running on.</em>
    225 </p>
    226 
    227 <p>
    228   Applications may have device-specific preferences or messaging (e.g., saving
    229   a device-specific playlist for a user in the cloud so that they can have a
    230   different playlist for their car and at home). A common solution is to
    231   leverage device identifiers such as <code>Device IMEI</code>, but this
    232   requires the <code>Device ID and call information</code>
    233   permission group (<code>PHONE</code> in M+). It also uses an identifier which
    234   cannot be reset and is shared across all apps.
    235 </p>
    236 
    237 <p>
    238   There are two alternatives to using these types of identifiers:
    239 </p>
    240 
    241 <ol>
    242   <li> Use the <code>com.google.android.gms.iid</code> InstanceID API.
    243   <code>getInstance(Context context).getID()<strong></code> </strong>will return a
    244   unique device identifier for your application instance. The
    245 result is an app instance scoped identifier that can be used as a key when
    246 storing information about the app and is reset if the user re-installs the app.
    247   <li> Create your own identifier thats scoped to your apps storage using basic
    248   system functions like <a
    249   href="{@docRoot}reference/java/util/UUID.html#randomUUID()"><code>randomUUID()</code></a>.</li>
    250 </ol>
    251 
    252 <h3 id="d_create_a_unique_identifier_for_advertising_or_user_analytics">Create a unique
    253 identifier for advertising or user analytics</h3>
    254 
    255 <p>
    256   <em>In this case, you need a unique identifier for building a profile for
    257   users who are not signed in to your app (e.g., for ads targeting or measuring
    258   conversions).</em>
    259 </p>
    260 
    261 <p>
    262   Building a profile for advertising and user analytics sometimes requires an
    263   identifier that is shared across other applications. Common solutions for
    264   this involve leveraging device identifiers such as <code>Device IMEI</code>,
    265   which requires the <code>Device ID</code> <code>and call information</code>
    266   permission group (<code>PHONE</code> in API level 23+) and cannot be reset by
    267   the user. In any of these cases, in addition to using a non-resettable
    268   identifier and requesting a permission that might seem unusual to users, you
    269   will also be in violation of the <a href=
    270   "https://play.google.com/about/developer-content-policy.html">Play Developer
    271   Program Policies</a>.
    272 </p>
    273 
    274 <p>
    275   Unfortunately, in these cases using the
    276   <code>com.google.android.gms.iid</code> InstanceID API or system functions to
    277   create an app-scoped ID are not appropriate solutions because the ID may need
    278   to be shared across apps. An alternative solution is to use the
    279   <code>Advertising Identifier</code> available from the <code><a href=
    280   "{@docRoot}reference/com/google/android/gms/ads/identifier/AdvertisingIdClient.Info.html">
    281   AdvertisingIdClient.Info</a></code> class via the <code>getId()</code>
    282   method. You can create an <code>AdvertisingIdClient.Info</code> object using
    283   the <code>getAdvertisingIdInfo(Context)</code> method and call the
    284   <code>getId()</code> method to use the identifier. <em><strong>Note that this
    285   method is blocking</strong></em>, so you should not call it from the main
    286   thread; a detailed explanation of this method is available <a href=
    287   "{@docRoot}google/play-services/id.html">here</a>.
    288 </p>
    289 
    290 <h2 id="know_the_libraries_you're_working_with">Know the Libraries You're
    291 Working With</h2>
    292 
    293 <p>
    294   Sometimes permissions are required by the libraries you use in your app. For
    295   example, ads and analytics libraries may require access to the
    296   <code>Location</code> or <code>Identity</code> permissions groups to
    297   implement the required functionality. But from the users point of view, the
    298   permission request comes from your app, not the library.
    299 </p>
    300 
    301 <p>
    302   Just as users select apps that use fewer permissions for the same
    303   functionality, developers should review their libraries and select
    304   third-party SDKs that are not using unnecessary permissions. For example, try
    305   to avoid libraries that require the <code>Identity</code> permission group
    306   unless there is a clear user-facing reason why the app needs those permissions.
    307   In particular, for libraries that provide location functionality, make sure you
    308   are not required to request the <code>FINE_LOCATION</code> permission unless
    309   you are using location-based targeting functionality.
    310 </p>
    311 
    312 <h2 id="be_transparent">Be Transparent</h2>
    313 
    314 <p>You should inform your users about what youre accessing and why. Research shows
    315 that users are much less uncomfortable with permissions requests if they know
    316 why the app needs them. A user study showed that:</p>
    317 
    318 <div style="padding:.5em 2em;">
    319 <div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
    320 <p>...a users willingness to grant a given permission to a given mobile app is
    321 strongly influenced by the purpose associated with such a permission. For
    322 instance a users willingness to grant access to his or her location will vary
    323 based on whether the request is required to support the apps core
    324 functionality or whether it is to share this information with an advertising
    325 network or an analytics company.<span
    326 style="font-size:.8em;color:#777"><sup><em><a
    327   href="#references" style="color:#777;padding-left:.1em;">1</a></em></sup></span></p>
    328 </div>
    329 </div>
    330 
    331 <p>
    332   Based on his groups research, Professor Jason Hong from CMU concluded that,
    333   in general:
    334 </p>
    335 
    336 <div style="padding:.5em 2em;">
    337 <div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
    338 <p>...when people know why an app is using something as sensitive as their location &mdash;
    339 for example, for targeted advertising &mdash; it makes them more comfortable than
    340 when simply told an app is using their location.<span
    341 style="font-size:.8em;color:#777"><sup><em><a
    342   href="#references" style="color:#777;padding-left:.1em;">1</a></em></sup></span></p>
    343 </div>
    344 </div>
    345 
    346 <p>
    347   As a result, if youre only using a fraction of the API calls that fall under
    348   a permission group, it helps to explicitly list which of those permissions
    349   you're using, and why. For example:
    350 </p>
    351 
    352 <ul>
    353   <li> If youre only using coarse location, let the user know this in your app
    354   description or in help articles about your app. </li>
    355   <li> If you need access to SMS messages to receive authentication codes that
    356   protect the user from fraud, let the user know this in your app description
    357   and/or the first time you access the data.</li>
    358 </ul>
    359 
    360 <p>
    361   Under certain conditions, it's also advantageous to let users know about
    362   sensitive data accesses in real-time. For example, if youre accessing the
    363   camera or microphone, its usually a good idea to let the user know with a
    364   notification icon somewhere in your app, or in the notification tray (if the
    365   application is running in the background), so it doesn't seem like you're
    366   collecting data surreptitiously.
    367 </p>
    368 
    369 <p>
    370   Ultimately, if you need to request a permission to make something in your app
    371   work, but the reason is not clear to the user, find a way to let the user
    372   know why you need the most sensitive permissions.
    373 </p>
    374 
    375 <h2 id="references">References</h2>
    376 
    377 <p>
    378   [1] <em>Modeling Users Mobile App Privacy Preferences: Restoring Usability
    379   in a Sea of Permission Settings</em>, by J. Lin B. Liu, N. Sadeh and J. Hong.
    380   In Proceedings of SOUPS 2014.
    381 </p>
    382