Doc change: Add best practices docs for permissions and ids.
Change-Id: I5756c6d1b87690ac26631ed7c18d27bf0b80ce36
diff --git a/docs/html/images/cards/card-user-ids_2x.png b/docs/html/images/cards/card-user-ids_2x.png
new file mode 100644
index 0000000..4db4f3c
--- /dev/null
+++ b/docs/html/images/cards/card-user-ids_2x.png
Binary files differ
diff --git a/docs/html/images/cards/card-user-permissions_2x.png b/docs/html/images/cards/card-user-permissions_2x.png
new file mode 100644
index 0000000..6abac48
--- /dev/null
+++ b/docs/html/images/cards/card-user-permissions_2x.png
Binary files differ
diff --git a/docs/html/images/cards/card-user_2x.png b/docs/html/images/cards/card-user_2x.png
new file mode 100644
index 0000000..e4ef23d
--- /dev/null
+++ b/docs/html/images/cards/card-user_2x.png
Binary files differ
diff --git a/docs/html/images/training/articles/user-data-overview-permissions-flow01.jpg b/docs/html/images/training/articles/user-data-overview-permissions-flow01.jpg
new file mode 100644
index 0000000..e3b192b
--- /dev/null
+++ b/docs/html/images/training/articles/user-data-overview-permissions-flow01.jpg
Binary files differ
diff --git a/docs/html/images/training/articles/user-data-overview-permissions-flow02.jpg b/docs/html/images/training/articles/user-data-overview-permissions-flow02.jpg
new file mode 100644
index 0000000..c2275eb
--- /dev/null
+++ b/docs/html/images/training/articles/user-data-overview-permissions-flow02.jpg
Binary files differ
diff --git a/docs/html/images/training/articles/user-data-overview-permissions-groups.png b/docs/html/images/training/articles/user-data-overview-permissions-groups.png
new file mode 100644
index 0000000..5996489
--- /dev/null
+++ b/docs/html/images/training/articles/user-data-overview-permissions-groups.png
Binary files differ
diff --git a/docs/html/images/training/articles/user-data-overview-permissions-usage.jpg b/docs/html/images/training/articles/user-data-overview-permissions-usage.jpg
new file mode 100644
index 0000000..0732369
--- /dev/null
+++ b/docs/html/images/training/articles/user-data-overview-permissions-usage.jpg
Binary files differ
diff --git a/docs/html/training/articles/user-data-ids.jd b/docs/html/training/articles/user-data-ids.jd
new file mode 100644
index 0000000..6541373
--- /dev/null
+++ b/docs/html/training/articles/user-data-ids.jd
@@ -0,0 +1,740 @@
+page.title=Best Practices for Unique Identifiers
+page.metaDescription=How to manage unique identifiers the right way for users.
+page.tags=ids, user data
+meta.tags="ids", "user data"
+page.image=images/cards/card-user-ids_2x.png
+
+page.article=true
+@jd:body
+
+<div id="tb-wrapper">
+<div id="tb">
+ <h2>In this document</h2>
+ <ol>
+ <li><a href="#tenets_of_working_with_android_identifiers">Tenets of Working with
+ Android Identifiers</a></li>
+ <li><a href="#version_specific_details_identifiers_in_m">Identifiers in Android 6.0+</a></li>
+ <li><a href="#working_with_advertising_ids">Working with Advertising IDs</a></li>
+ <li><a href="#working_with_instance_ids_&_guids">Working with Instance IDs and GUIDs</a></li>
+ <li><a href="#understand_identifier_characteristics">Understanding Identifier
+ Characteristics</a>
+ <ol>
+ <li><a href="#scope">Scope</a></li>
+ <li><a href="#resettability_&_persistence">Resettability & persistence</a></li>
+ <li><a href="#uniqueness">Uniqueness</h3>
+ <li><a href="#integrity_protection_and_non-repudiability">Integrity protection and
+ non-repudiability</a></li>
+ </ol>
+ </li>
+ <li><a href="#use_appropriate_identifiers">Common Use Cases and the Identifier to Use</a>
+ <ol>
+ <li><a href="#a_track_signed-out_user_preferences">Tracking signed-out user
+ preferences</a></li>
+ <li><a href="#b_track_signed-out_user_behavior">Tracking signed-out user behavior</a></li>
+ <li><a href="#c_generate_signed-out_anonymous_user_analytics">Generating
+ signed-out/anonymous user analytics</a></li>
+ <li><a href="#d_track_signed-out_user_conversion">Tracking signed-out user
+ conversion</a></li>
+ <li><a href="#e_handle_multiple_installations">Handling multiple installations</a></li>
+ <li><a href="#f_anti-fraud_enforcing_free_content_limits_detecting_sybil_attacks">Anti-fraud:
+ Enforcing free content limits / detecting Sybil attacks</a></li>
+ <li><a href="#g_manage_telephony_&_carrier_functionality">Managing telephony and carrier
+ functionality</a></li>
+ <li><a href="#h_abuse_detection_identifying_bots_and_ddos_attacks">Abuse detection:
+ Identifying bots and DDoS attacks</a></li>
+ <li><a href="#i_abuse_detection_detecting_high_value_stolen_credentials">Abuse detection:
+ Detecting high value stolen credentials</a></li>
+ </ol>
+ </li>
+ </ol>
+ </div>
+</div>
+
+<p>
+ While there are valid reasons why your application may need to identify a
+ device rather than an instance of the application or an authenticated user on
+ the device, for the vast majority of applications, the ultimate goal is to
+ identify a particular <em>installation</em> of your app (not the actual
+ physical device).
+</p>
+
+<p>
+ Fortunately, identifying an installation on Android is straightforward using
+ an Instance ID or by creating your own GUID at install time. This document
+ provides guidance for selecting appropriate identifiers for your application,
+ based on your use-case.
+</p>
+
+<p>
+ For a general look at Android permissions, please see <a href=
+ "{@docRoot}training/articles/user-data-overview.html">Permissions
+ and User Privacy</a>. For specific best practices for
+ working with Android permissions, please see <a href=
+ "{@docRoot}training/articles/user-data-permissions.html">Best Practices for
+ App Permissions</a>.
+</p>
+
+
+<h2 id="tenets_of_working_with_android_identifiers">Tenets of Working with Android Identifiers</h2>
+
+<p>
+ We recommend that you follow these tenets when working with Android
+ identifiers:
+</p>
+
+<p>
+ <em><strong>#1: Avoid using hardware identifiers.</strong></em> Hardware
+ identifiers such as SSAID (Android ID) and IMEI can be avoided in most
+ use-cases without limiting required functionality.
+</p>
+
+<p>
+ <em><strong>#2: Only use Advertising ID for user profiling or ads
+ use-cases.</strong></em> When using an <a href=
+ "https://support.google.com/googleplay/android-developer/answer/6048248?hl=en">
+ Advertising ID</a>, always respect the <a href=
+ "https://play.google.com/about/developer-content-policy.html#ADID">Limit Ad
+ Tracking</a> flag, ensure the identifier cannot be connected to personally
+ identifiable information (PII) and avoid bridging Advertising ID resets.
+</p>
+
+<p>
+ <em><strong>#3: Use an Instance ID or a privately stored GUID whenever
+ possible for all other use-cases except payment fraud prevention and
+ telephony.</strong></em> For the vast majority of non-ads use-cases, an
+ instance ID or GUID should be sufficient.
+</p>
+
+<p>
+ <em><strong>#4: Use APIs that are appropriate to your use-case to minimize
+ privacy risk.</strong></em> Use the
+ <a href="http://source.android.com/devices/drm.html">DRM
+ API</a> API for high value content
+ protection and the <a href="{@docRoot}training/safetynet/index.html">SafetyNet
+ API</a> for abuse prevention. The Safetynet API is
+ the easiest way to determine whether a device is genuine without incurring
+ privacy risk.
+</p>
+
+<p>
+ The remaining sections of this guide elaborate on these rules in the context
+ of developing Android applications.
+</p>
+
+<h2 id="version_specific_details_identifiers_in_m">Identifiers in Android 6.0+</h2>
+
+<p>
+ MAC addresses are globally unique, not user-resettable and survive factory
+ reset. It is generally not recommended to use MAC address for any form of
+ user identification. As a result, as of Android M, local device MAC addresses
+ (for example, Wifi and Bluetooth) <em><strong>are not available via third party
+ APIs</strong></em>. The {@link android.net.wifi.WifiInfo#getMacAddress WifiInfo.getMacAddress()}
+ method and the {@link android.bluetooth.BluetoothAdapter#getAddress
+ BluetoothAdapter.getDefaultAdapter().getAddress()} method will
+ both return <code>02:00:00:00:00:00</code>..
+</p>
+
+<p>
+ Additionally, you must hold the following permissions to access MAC addresses
+ of nearby external devices available via Bluetooth and Wifi scans:
+</p>
+
+<table>
+ <tr>
+ <th><strong>Method/Property</strong></td>
+ <th><strong>Permissions Required</strong></td>
+ </tr>
+ <tr>
+ <td>
+ <code><a href="{@docRoot}reference/android/net/wifi/WifiManager.html#getScanResults()">WifiManager.getScanResults()</a></code>
+ </td>
+ <td>
+ <code>ACCESS_FINE_LOCATION</code> or <code>ACCESS_COARSE_LOCATION</code>
+ </td>
+ </tr>
+ <tr>
+ <td>
+ <code><a href="{@docRoot}reference/android/bluetooth/BluetoothDevice.html#ACTION_FOUND">BluetoothDevice.ACTION_FOUND</a></code>
+ </td>
+ <td>
+ <code>ACCESS_FINE_LOCATION</code> or <code>ACCESS_COARSE_LOCATION</code>
+ </td>
+ </tr>
+ <tr>
+ <td>
+ <code><a href="{@docRoot}reference/android/bluetooth/le/BluetoothLeScanner.html#startScan(android.bluetooth.le.ScanCallback)">BluetoothLeScanner.startScan(ScanCallback)</a></code>
+ </td>
+ <td>
+ <code>ACCESS_FINE_LOCATION</code> or <code>ACCESS_COARSE_LOCATION</code>
+ </td>
+ </tr>
+</table>
+
+
+<h2 id="working_with_advertising_ids">Working with Advertising IDs</h2>
+
+<p>
+ Advertising ID is a user-resettable identifier and is appropriate for Ads
+ use-cases, but there are some key points to bear in mind when using it:
+</p>
+
+<p>
+ <em><strong>Always respect the user’s intention in resetting the advertising
+ ID</strong></em>. Do not bridge user resets by using a more persistent device
+ identifier or fingerprint to link subsequent Advertising IDs together without
+ the user’s consent. The <a href=
+ "https://play.google.com/about/developer-content-policy.html">Google Play
+ Developer Content Policy</a> states:
+</p>
+
+<div style="padding:.5em 2em;">
+<div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
+<p>...upon reset, a new advertising
+ identifier must not be connected to a previous advertising identifier or data
+ derived from a previous advertising identifier without the explicit consent
+ of the user</span></p>
+</div>
+</div>
+
+<p>
+ <em><strong>Always respect the associated Interest Based Advertising
+ flag</strong></em>. Advertising IDs are configurable in that users can limit
+ the amount of tracking associated with the ID. Always use the <code><a href=
+ "https://developers.google.com/android/reference/com/google/android/gms/ads/identifier/AdvertisingIdClient.Info.html#isLimitAdTrackingEnabled()">
+ AdvertisingIdClient.Info.isLimitAdTrackingEnabled()</a></code> method to
+ ensure you are not circumventing your users' wishes. The <a href=
+ "https://play.google.com/about/developer-content-policy.html">Google Play
+ Developer Content Policy</a> states:
+</p>
+
+
+<div style="padding:.5em 2em;">
+<div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
+<p>...you must abide by a user’s ‘opt out of
+ interest-based advertising’ setting. If a user has enabled this setting, you
+ may not use the advertising identifier for creating user profiles for
+ advertising purposes or for targeting users with interest-based advertising.
+ Allowed activities include contextual advertising, frequency capping,
+ conversion tracking, reporting and security and fraud detection.</span></p>
+</div>
+</div>
+
+<p>
+ <em><strong>Be aware of any privacy or security policies associated with SDKs
+ you use that are related to Advertising ID use.</strong></em> For example, if
+ you are using the Google Analytics SDK
+ <code><a href=
+ "https://developers.google.com/android/reference/com/google/android/gms/analytics/Tracker.html#enableAdvertisingIdCollection(boolean)">mTracker.enableAdvertisingIdCollection(true)</a></code>
+ method, make sure to review and adhere to all applicable <a href=
+ "https://developers.google.com/analytics/devguides/collection/android/v4/policy">
+ Analytics SDK policies</a>.
+</p>
+
+<p>
+ Also, be aware that the <a href=
+ "https://play.google.com/about/developer-content-policy.html">Google Play
+ Developer Content Policy</a> requires that the Advertising ID “must not be
+ connected to personally-identifiable information or associated with any
+ persistent device identifier (for example: SSAID, MAC address, IMEI, etc.,)
+ without the explicit consent of the user.”
+</p>
+
+<p>
+ As an example, suppose you want to collect information to populate database
+ tables with the following columns:
+</p>
+
+<table>
+ <tr>
+ <td>
+ <table>
+ <tr>
+ <td class="tab2">
+ <code>timestamp</code></td>
+ <td class="tab2">
+ <code>ad_id</code></td>
+ <td>
+ <code><strong>account_id</strong></code></td>
+ <td class="tab2">
+ <code>clickid</code></td>
+ </tr>
+ </table>
+
+ <p>TABLE-01</p>
+ </td>
+ <td>
+ <table>
+ <tr>
+ <td>
+ <code><strong>account_id</strong></code></td>
+ <td class="tab2">
+ <code>name</code></td>
+ <td class="tab2">
+ <code>dob</code></td>
+ <td class="tab2">
+ <code>country</code></td>
+ </tr>
+ </table>
+ <p>TABLE-02</p>
+ </td>
+ </tr>
+</table>
+
+
+<p>
+ In this example, the <code>ad_id</code> column could be joined to PII via the
+ <code>account_id</code> column in both tables, which would be a violation of
+ the <a href=
+ "https://play.google.com/about/developer-content-policy.html">Google Play
+ Developer Content Policy</a>.
+</p>
+
+<p>
+ Keep in mind that links between Advertiser ID and PII aren't always this
+ explicit. It's possible to have “quasi-identifiers” that appear in both PII
+ and Ad ID keyed tables, which also cause problems. For example, assume we
+ change TABLE-01 and TABLE-02 as follows:
+</p>
+
+<table>
+ <tr>
+ <td><table>
+ <tr>
+ <td>
+ <code><strong>timestamp</strong></code></td>
+ <td class="tab2">
+ <code>ad_id</code></td>
+ <td>
+ <code>clickid</code></td>
+ <td>
+ <code><strong>dev_model</strong></code></td>
+ </tr>
+ </table>
+
+ </pre>
+ <p>TABLE-01</p>
+ </td>
+ <td>
+ <table>
+ <tr>
+ <td>
+ <code><strong>timestamp</strong></code></td>
+ <td class="tab2">
+ <code>demo</code></td>
+ <td class="tab2">
+ <code>account_id</code></td>
+ <td>
+ <code><strong>dev_model</strong></code></td>
+ <td class="tab2">
+ <code>name</code></td>
+ </tr>
+ </table>
+ <p>TABLE-02</p>
+ </td>
+ </tr>
+</table>
+
+
+<p>
+ In this case, with sufficiently rare click events, it's still possible to
+ join between the Advertiser ID TABLE-01 and the PII contained in TABLE-2
+ using the timestamp of the event and the device model.
+</p>
+
+<p>
+ While it is often difficult to guarantee that no such quasi-identifiers exist
+ in a dataset, the most obvious join risks can be prevented by generalizing
+ unique data where possible. In the example, this would mean reducing the
+ accuracy of the timestamp so that multiple devices with the same model appear
+ for every timestamp.
+</p>
+
+<p>
+ Other solutions include:
+</p>
+
+<ul>
+<li><em><strong>Not designing tables that explicitly link PII with Advertising
+IDs</strong></em>. In the first example above this would mean not including the
+account_id column in TABLE-01.</li>
+
+<li><em><strong>Segregating and monitoring access control lists for users or roles
+that have access to both the Advertising ID keyed data and PII</strong></em>. If the
+ability to access both sources simultaneously (for example, to perform
+a join between two tables) is tightly controlled and audited, it reduces the
+risk of association between the Advertising ID and PII. Generally speaking,
+controlling access means:
+
+<ol>
+ <li> Keeping access control lists (ACLs) for Advertiser ID keyed data and PII disjoint to
+ minimize the number of individuals or roles that are in both ACLs, and</li>
+ <li> Implementing access logging and auditing to detect and manage any exceptions to
+ this rule.</li>
+</ol>
+</li>
+</ul>
+
+<p>
+ For more information on working responsibly with Advertising IDs, please see
+ the <a href=
+ "https://support.google.com/googleplay/android-developer/answer/6048248?hl=en">
+ Advertising ID</a> help center article.
+</p>
+
+<h2 id="working_with_instance_ids_&_guids">Working with Instance IDs and GUIDs</h2>
+
+<p>
+ The most straightforward solution to identifying an application instance
+ running on a device is to use an Instance ID, and this is the recommended
+ solution in the majority of non-ads use-cases. Only the app instance for
+ which it was provisioned can access this identifier, and it's (relatively)
+ easily resettable because it only persists as long as the app is installed.
+</p>
+
+<p>
+ As a result, Instance IDs provide better privacy properties compared to
+ non-resettable, device-scoped hardware IDs. They also come with a key-pair
+ for message signing (and similar actions) and are available on Android, iOS
+ and Chrome. Please see the <a href=
+ "https://developers.google.com/instance-id/">What is Instance ID?</a> help
+ center document for more information.
+</p>
+
+<p>
+ In cases where an Instance ID isn't practical, custom globally unique IDs
+ (GUIDs) can also be used to uniquely identify an app instance. The simplest
+ way to do so is by generating your own GUID using the following code.
+</p>
+
+<pre>String uniqueID = UUID.randomUUID().toString();</pre>
+
+<p>
+ Because the identifier is globally unique, it can be used to identify a
+ specific app instance. To avoid concerns related to linking the identifier
+ across applications, GUIDs should be stored in internal storage rather than
+ external (shared) storage. Please see <a href=
+ "{@docRoot}guide/topics/data/data-storage.html">Storage Options</a> guide for
+ more information.
+</p>
+
+
+<h2 id="understand_identifier_characteristics">Understanding Identifier Characteristics</h2>
+
+<p>
+ The Android Operating system offers a number of IDs with different behavior
+ characteristics and which ID you should use depends on how those following
+ characteristics work with your use-case. But these characteristics also come
+ with privacy implications so it's important to understand how these
+ characteristics play together.
+</p>
+
+<h3 id="scope">Scope</h3>
+
+<p>
+ Identifier scope explains which systems can access the identifier. Android
+ identifier scope generally comes in three flavors:
+</p>
+
+<ul>
+ <li> <em>Single app</em>. the ID is internal to the app and not accessible to other apps.
+ <li> <em>Group of apps</em> - the ID is accessible to a pre-defined group of related apps.
+ <li> <em>Device</em> - the ID is accessible to all apps installed on the device.
+</ul>
+
+<p>
+ The wider the scope granted to an identifier, the greater the risk of it
+ being used for tracking purposes. Conversely, if an identifier can only be
+ accessed by a single app instance, it can’t be used to track a device across
+ transactions in different apps.
+</p>
+<h3 id="resettability_&_persistence">Resettability and persistence</h3>
+
+<p>
+ Resettability and persistence define the lifespan of the identifier and
+ explain how it can be reset. Common reset triggers are: in-app resets, resets
+ via System Settings, resets on launch, and resets on installation. Android
+ Identifiers can have varying lifespans, but the lifespan is usually related
+ to how the ID is reset:
+</p>
+<ul>
+ <li> <em>Session-only</em> - a new ID is used every time the user restarts the app.
+ <li> <em>Install-reset</em> - a new ID is used every time user uninstalls and reinstalls the app.
+ <li> <em>FDR-reset</em> - a new ID is used every time the user factory-resets the device.
+ <li> <em>FDR-persistent</em> - the ID survives factory reset.
+</ul>
+
+<p>
+ Resettability gives users the ability to create a new ID that is
+ disassociated from any existing profile information. This is important
+ because the longer, and more reliably, an identifier persists (e.g. across
+ factory resets etc.), the greater the risk that the user may be subjected to
+ long-term tracking. If the identifier is reset upon app reinstall, this
+ reduces the persistence and provides a means for the ID to be reset, even if
+ there is no explicit user control to reset it from within the app or the
+ System Settings.
+</p>
+<h3 id="uniqueness">Uniqueness</h3>
+
+<p>
+ Uniqueness establishes the likelihood that identical identifiers exist within
+ the associated scope. At the highest level, a globally unique identifier will
+ never have a collision - even on other devices/apps. Otherwise, the level of
+ uniqueness depends on the size of the identifier and the source of randomness
+ used to create it. For example, the chance of a collision is much higher for
+ random identifiers seeded with the calendar date of installation (e.g.,
+ 2015-01-05) than for identifiers seeded with the Unix timestamp of
+ installation (e.g., 1445530977).
+</p>
+
+<p>
+ In general, user account identifiers can be considered unique (i.e., each
+ device/account combo has a unique ID). On the other hand, the less the unique
+ an identifier is within a population (e.g. of devices), the greater the
+ privacy protection because it's less useful for tracking an individual user.
+</p>
+
+<h3 id="integrity_protection_and_non-repudiability">Integrity protection and
+non-repudiability</h3>
+
+<p>
+ An identifier that is difficult to spoof or replay can be used to prove that
+ the associated device or account has certain properties (e.g. it’s not a
+ virtual device used by a spammer). Difficult to spoof identifiers also
+ provide <em>non-repudiability</em>. If the device signs a message with a
+ secret key, it is difficult to claim someone else’s device sent the message.
+ Non-repudiability could be something a user wants (e.g. authenticating a
+ payment) or it could be an undesirable property (e.g. sending a message they
+ regret).
+</p>
+
+
+<h2 id="use_appropriate_identifiers">Common Use Cases and the Identifier to Use</h2>
+
+<p>
+ This section provides alternatives to using hardware IDs such as IMEI or
+ SSAID for the majority of use-cases. Relying on hardware IDs is discouraged
+ because the user cannot reset them and generally has limited control over
+ their collection.
+</p>
+
+<h3 id="a_track_signed-out_user_preferences">Tracking signed-out user preferences</h3>
+
+<p>
+ <em>In this case, you are saving per-device state on the server side.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: Instance ID or a GUID.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ Persisting information through reinstalls is not recommended because users
+ may want to reset their preferences by reinstalling the app.
+</p>
+
+<h3 id="b_track_signed-out_user_behavior">Tracking signed-out user behavior</h3>
+
+<p>
+ <em>In this case, you have created a profile of a user based on their
+ behavior across different apps/sessions on the same device.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: Advertising ID.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ Use of the Advertising ID is mandatory for Advertising use-cases per the
+ <a href="https://play.google.com/about/developer-content-policy.html">Google
+ Play Developer Content Policy</a> because the user can reset it.
+</p>
+
+<h3 id="c_generate_signed-out_anonymous_user_analytics">Generating signed-out/anonymous user analytics</h3>
+
+<p>
+ <em>In this case, you are measuring usage statistics and analytics for
+ signed-out or anonymous users.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: Instance ID; if an Instance ID is
+ insufficient, you can also use a GUID.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ An Instance ID or a GUID is scoped to the app that creates it, which prevents
+ it from being used to track users across apps. It is also easily reset by
+ clearing app data or reinstalling the app. Creating Instance IDs and GUIDs is
+ straightforward:
+</p>
+
+<ul>
+ <li> Creating an Instance ID: <code>String iid = InstanceID.getInstance(context).getId()</code>
+ <li> Creating a GUID: <code>String uniqueID = UUID.randomUUID().toString</code>
+</ul>
+
+<p>
+ Be aware that if you have told the user that the data you are collecting is
+ anonymous, you should <em><strong>ensure you are not connecting the
+ identifier to PII</strong></em> or other identifiers that may be linked to
+ PII.
+</p>
+
+<p>
+ You can also use Google Analytics for Mobile Apps, which offers a solution
+ for per-app analytics.
+</p>
+
+<h3 id="d_track_signed-out_user_conversion">Tracking signed-out user conversion</h3>
+
+<p>
+ <em>In this case, you are tracking conversions to detect if your marketing
+ strategy was successful.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: Advertising ID.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ This is an ads-related use-case which may require an ID that is available
+ across different apps so using an Advertising ID is the most appropriate
+ solution.
+</p>
+
+<h3 id="e_handle_multiple_installations">Handling multiple installations</h3>
+
+<p>
+ <em>In this case, you need to identify the correct instance of the app when
+ it's installed on multiple devices for the same user.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: Instance ID or GUID.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ Instance ID is designed explicitly for this purpose; its scope is limited to
+ the app so that it cannot be used to track users across different apps and it
+ is reset upon app reinstall. In the rare cases where an Instance ID is
+ insufficient, you can also use a GUID.
+</p>
+
+<h3 id="f_anti-fraud_enforcing_free_content_limits_detecting_sybil_attacks">Anti-fraud: Enforcing free content limits / detecting Sybil attacks</h3>
+
+<p>
+ <em>In this case, you want to limit the number of free content (e.g.
+ articles) a user can see on a device.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: Instance ID or GUID.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ Using a GUID or Instance ID forces the user to reinstall the app in order to
+ overcome the content limits, which is a sufficient burden to deter most
+ people. If this is not sufficient protection, Android provides a
+ <a href="http://source.android.com/devices/drm.html">DRM API</a>
+ which can be used to limit access to content.
+</p>
+
+<h3 id="g_manage_telephony_&_carrier_functionality">Managing telephony and carrier functionality</h3>
+
+<p>
+ <em>In this case, your app is interacting with the device's phone and texting
+ functionality.</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: IMEI, IMSI, and Line1.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ Leveraging hardware identifiers is acceptable if it is required for
+ telephony/carrier related functionality; for example, switching between
+ cellular carriers/SIM slots or delivering SMS messages over IP (for Line1) -
+ SIM-based user accounts. But it's important to note that in Android 6.0+
+ these identifiers can only be used via a runtime permission and that users
+ may toggle off this permission so your app should handle these exceptions
+ gracefully.
+</p>
+
+<h3 id="h_abuse_detection_identifying_bots_and_ddos_attacks">Abuse detection:
+Identifying bots and DDoS attacks</h3>
+
+<p>
+ <em>In this case, you are trying to detect multiple fake devices attacking
+ your backend services.</em>
+</p>
+
+<p>
+ <strong>We Recommend:</strong> The Safetynet API.
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ An identifier in isolation does little to indicate that a device is genuine.
+ You can verify that a request comes from a genuine Android device (as opposed
+ to an emulator or other code spoofing another device) using the Safetynet
+ API's <code>SafetyNet.SafetyNetApi.attest(mGoogleApiClient, nonce)</code>
+ method to verify the integrity of a device making a request. For more
+ detailed information, please see <a href=
+ "{@docRoot}training/safetynet/index.html">Safetynet's API documentation</a>.
+</p>
+
+<h3 id="i_abuse_detection_detecting_high_value_stolen_credentials">Abuse detection:
+Detecting high value stolen credentials</h3>
+
+<p>
+ <em>In this case, you are trying to detect if a single device is being used
+ multiple times with high-value, stolen credentials (e.g. to make fraudulent
+ payments).</em>
+</p>
+
+<p>
+ <strong>We Recommend</strong>: IMEI/IMSI (requires <code>PHONE</code>
+ permission group in Android 6.0 (API level 23) and higher.)
+</p>
+
+<p>
+ <strong>Why this Recommendation?</strong>
+</p>
+
+<p>
+ With stolen credentials, devices can be used to monetize multiple high value
+ stolen credentials (such as tokenized credit cards). In these scenarios,
+ software IDs can be reset to avoid detection, so hardware identifiers may be
+ used.
+</p>
\ No newline at end of file
diff --git a/docs/html/training/articles/user-data-overview.jd b/docs/html/training/articles/user-data-overview.jd
new file mode 100644
index 0000000..109826a
--- /dev/null
+++ b/docs/html/training/articles/user-data-overview.jd
@@ -0,0 +1,266 @@
+page.title=Permissions and User Privacy
+page.metaDescription=An overview of permissions on Android and how to manage them.
+page.tags="user data","permissions","identifiers"
+page.image=images/cards/card-user_2x.png
+
+page.article=true
+@jd:body
+
+<div id="tb-wrapper">
+<div id="tb">
+ <h2>In this document</h2>
+ <ol>
+ <li><a href="#introduction">Introduction</a></li>
+ <li><a href="#permission_groups">Permission Groups</a></li>
+ <li><a href="#permission_requests_and_app_downloads">Permission
+ Requests and App Downloads</a></li>
+ <li><a href="#permission_requests_trend_downward">Permission Requests
+ Trend Downward</a></li>
+ </ol>
+ <h2>You should also read</h2>
+ <ol>
+ <li><a href="{@docRoot}guide/topics/security/permissions.html">System Permissions</a></li>
+ <li><a href="{@docRoot}training/permissions/index.html">Working with System
+ Permissions</a></li>
+ </ol>
+ </div>
+</div>
+
+<p>
+ Permissions protect sensitive information available from a device and should
+ only be used when access to information is necessary for the functioning of
+ your app.
+</p>
+
+<p>
+ This document provides a high-level overview on how permissions work in
+ Android so you can make better, more informed decisions about the permissions
+ you're requesting. The information in this document is not use-case specific
+ and avoids complex, low-level discussions of the underlying code.
+</p>
+
+<p>
+ For specific recommendations on how to manage permissions, please see
+ <a href="{@docRoot}training/articles/user-data-permissions.html">Best
+ Practices for App Permissions</a>. For best practices on using unique
+ identifiers on Android, please see <a href=
+ "{@docRoot}training/articles/user-data-ids.html">Best Practices for Unique
+ Identifiers</a>. For details on how to work with permissions in your code,
+ see <a href="{@docRoot}training/permissions/index.html">Working with System
+ Permissions</a>.
+</p>
+
+
+<h2 id="introduction">Introduction</h2>
+
+<p>
+ Every Android application must have a <em>manifest file</em> that presents
+ essential information about the app to the Android system. The Android system
+ also requires apps to request permission when they want to access sensitive
+ device or user information, and these requests must be documented in advance
+ as a part of your app's manifest. Moreover, accessing sensitive information
+ can affect user behavior, so it's important to make sure you are only making
+ permission requests when that information is necessary for the functioning of
+ your app.
+</p>
+
+
+<h2 id="permission_groups">Permission Groups</h2>
+
+<p>
+ Permissions in Android are organized into <code><a href=
+ "{@docRoot}guide/topics/security/permissions.html#perm-groups">permission
+ groups</a></code> that organize, and group, permissions related to a device's
+ capabilities or features. Under this system, permission requests are handled
+ at the group level and a <em><strong>single permission group</strong></em>
+ corresponds to <em><strong>several permission declarations</strong></em> in
+ the app manifest; for example, the SMS group includes both the
+ <code>READ_SMS</code> and the <code>WRITE_SMS</code> declarations.
+</p>
+
+
+<div class="wrap">
+ <img src="{@docRoot}images/training/articles/user-data-overview-permissions-flow01.jpg">
+</div>
+
+<p>
+ This arrangement is simpler and more informative for users; once an app is
+ granted permission to access the group, it can use API calls within that
+ group and users with auto-update enabled will not be asked for additional
+ permissions because they have already granted access to the group. Grouping
+ permissions in this way enables the user to make more meaningful and informed
+ choices, without being overwhelmed by complex and technical permission
+ requests.
+</p>
+
+<p>
+ This also means that when you request access to a particular API call or
+ query a content provider behind a permission, the user will be presented with
+ a request to grant permission for the whole group rather than the specific
+ API call. For example, if you request the <code>MANAGE_ACOUNTS</code>
+ permission, the user will be asked to grant access to the <em>Identity</em>
+ group which is composed of the <code>GET_ACCOUNTS</code>,
+ <code>READ_PROFILE</code>, and <code>WRITE_PROFILE</code> permissions, and
+ all their associated methods.
+</p>
+
+<div class="wrap">
+ <img src="{@docRoot}images/training/articles/user-data-overview-permissions-flow02.jpg">
+</div>
+
+<p>
+ One consequence of grouping permissions is that a single API call within your
+ app can have a multiplying effect in terms of the number of permissions
+ requested by your app.
+</p>
+
+<ol>
+<li>API Call →</li>
+<li stydle="margin-left:.5em;">Triggers a specific <em>Permission Group</em> access
+request →</li>
+<li stydle="margin-left:1em;">Successful request grants access to all permissions in
+group (if auto-update
+enabled) →</li>
+<li stydle="margin-left:1.5em;">Each permission grants access to all APIs under that
+permission</li>
+</ol>
+
+<p>
+ As another example, let's assume your application uses one or more <a href=
+ "{@docRoot}reference/android/telephony/TelephonyManager.html"><code>TelephonyManager</code></a>
+ methods, such as:
+</p>
+
+<pre class="prettyprint">
+TelephonyManager.getDeviceId()
+TelephonyManager.getSubscriberId()
+TelephonyManager.getSimSerialNumber()
+TelephonyManager.getLine1Number()
+TelephonyManager.getVoiceMailNumber()
+</pre>
+
+<p>
+ To use these methods, the <code>READ_PHONE_STATE</code> permission must be
+ declared in the app's manifest, and the associated permission group,
+ <em>Device ID and Call information</em>, will be surfaced to the user. This
+ is important, because it means the user will be asked to grant permission for
+ the relevant group and all its associated permissions and API calls, rather
+ than for the specific API call you're requesting.
+</p>
+
+<p>For a full mapping between permissions and their associated permission groups,
+please refer to the appropriate version-specific documentation below:</p>
+
+<ul>
+ <!--<li> <a href="">pre-M Android OS versions</a>.</li> -->
+ <li> <a href="{@docRoot}guide/topics/security/permissions.html#perm-groups">Permission
+ groups, Android 6.0 Marshmallow (API level 23) and later</a>.</li>
+</ul>
+
+
+<h2 id="permission_requests_and_app_downloads">Permission Requests and App Downloads</h2>
+
+<div style="padding:.5em 2em;">
+<div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
+<p><em>I'm currently using the READ_PHONE_STATE permission in Android to pause my
+media player when there's a call, and to resume playback when the call is over.
+The permission seems to scare a lot of people</em>...<span
+style="font-size:.8em;color:#777"><sup><em><a
+href="#references" style="color:#777;padding-left:.1em;">1</a></em></span></p>
+</div>
+</div>
+
+<p>
+ Research shows that among apps that are otherwise identical (e.g.,
+ functionality, brand recognition), requesting fewer permissions leads to more
+ downloads. Publicly available sources exist that assign grades to apps based
+ on their permissions usage and allow users to compare related apps by score;
+ such grades exist for many of the current Android apps and users pay close
+ attention to the related rankings.
+</p>
+
+<p>
+ One study<span style="font-size:.8em;color:#777"><sup><em><a href=
+ "#references" style=
+ "color:#777;padding-left:.1em;">2</a></em></sup></span><sup>, in which users
+ were shown two unbranded apps with similar ratings that had the same
+ functionality but different sets of permission requests, showed that users
+ were, on average, 3 times more likely to install the app with fewer
+ permissions requests. And a similar study<span style=
+ "font-size:.8em;color:#777"><sup><em><a href="#references" style=
+ "color:#777;padding-left:.1em;">3</a></em></sup> showed that users are 1.7
+ times more likely, on average, to select the application with fewer
+ permission requests.</span></sup>
+</p>
+
+<p>
+ <sup>Finally, permissions usage is not evenly distributed across apps within
+ a similar category of Play apps. For example, 39.3% of arcade game apps in
+ the Play store request no permissions that are surfaced to the user while
+ only 1.5% of arcade games request the Phone permission group (see Figure
+ 1).</sup>
+</p>
+
+<div class="wrap">
+ <div class="cols">
+ <div class="col-16of16">
+ <img src="{@docRoot}images/training/articles/user-data-overview-permissions-groups.png">
+ <p class="figure-caption"><strong>Figure 1.</strong> Distribution of
+ permission groups use across Arcade Games category.</p>
+ </div>
+ </div>
+</div>
+
+<p>
+ Users comparing your app to other similar apps may determine that it is
+ making unusual permission requests for that category - in this case, Arcade
+ Games apps accessing the <em>Phone</em> permission group. As a result, they
+ may install a similar app in that category that avoids those
+ requests.<span style="font-size:.8em;color:#777"><sup><em><a href=
+ "#references" style="color:#777;padding-left:.1em;">4</a></em></sup></span>
+</p>
+
+
+<h2 id="permission_requests_trend_downward">Permission Requests Trend Downward</h2>
+
+<p>
+ A recent analysis of Play store apps over time indicated that many developers
+ trim permissions after first publishing their apps, suggesting that they may
+ be employing more caution around which permission groups they declare.
+</p>
+
+<div class="wrap">
+ <div class="cols">
+ <div class="col-16of16">
+ <img src="{@docRoot}images/training/articles/user-data-overview-permissions-usage.jpg">
+ <p class="figure-caption"><strong>Figure 2.</strong> Developer usage of popular
+ permissions has decreased over time.</p>
+ </div>
+ </div>
+</div>
+
+<p>
+ The graph in <em>Figure 2</em> illustrates this trend. There has been a
+ steady decrease in the average percentage of developers' apps requesting at
+ least one of the three most popular permissions in the Play store
+ (<code>READ_PHONE_STATE</code>, <code>ACCESS_FINE_LOCATION</code>, and
+ <code>ACCESS_COARSE_LOCATION</code>). These results indicate that developers
+ are reducing the permissions their apps request in response to user behavior.
+</p>
+
+<p>
+ The bottom line is that providing the same functionality to the user with
+ minimal access to sensitive information means more downloads for your app.
+ For specific recommendations on how to achieve this, please see <a href=
+ "{@docRoot}training/articles/user-data-permissions.html">Best Practices for
+ Application Permissions</a>.
+</p>
+
+
+<h2 id="references">References</h2>
+
+<p>[1] Developer quote on StackOverflow. <em>(<a
+ href="http://stackoverflow.com/questions/24374701/alternative-to-read-phone-state-permission-for-getting-notified-of-call">source</a>)</em></p>
+<p>[2] <em>Using Personal Examples to Improve Risk Communication for Security and Privacy Decisions</em>, by M. Harbach, M. Hettig, S. Weber, and M. Smith. In Proceedings of ACM CHI 2014.</p>
+<p>[3] <em>Modeling Users’ Mobile App Privacy Preferences: Restoring Usability in a Sea of Permission Settings</em>, by J. Lin B. Liu, N. Sadeh and J. Hong. In Proceedings of SOUPS 2014.</p>
+<p>[4] <em>Teens and Mobile Apps Privacy. (<a href="http://www.pewinternet.org/files/old-media/Files/Reports/2013/PIP_Teens%20and%20Mobile%20Apps%20Privacy.pdf">source</a>)</em></p>
diff --git a/docs/html/training/articles/user-data-permissions.jd b/docs/html/training/articles/user-data-permissions.jd
new file mode 100644
index 0000000..99f14b9
--- /dev/null
+++ b/docs/html/training/articles/user-data-permissions.jd
@@ -0,0 +1,381 @@
+page.title=Best Practices for App Permissions
+page.metaDescription=How to manage permissions to give users context and control.
+page.tags=permissions, user data
+meta.tags="permissions", "user data"
+page.image=images/cards/card-user-permissions_2x.png
+
+page.article=true
+@jd:body
+
+<div id="tb-wrapper">
+<div id="tb">
+ <h2>In this document</h2>
+ <ol>
+ <li><a href="#tenets_of_working_with_android_permissions">Tenets</a></li>
+ <li><a href="#version_specific_details_permissions_in_m">Permissions in Android
+ 6.0+</h2></a></li>
+ <li><a href="#avoid_requesting_unnecessary_permissions">Avoid Requesting
+Unnecessary Permissions</h2></a>
+ <ol>
+ <li><a href="#a_camera_contact_access_with_real-time_user_requests">Camera/Contact
+ access with realtime user requests</a></li>
+ <li><a href="#b_running_in_the_background_after_losing_audio_focus">Running in
+the background after losing audio focus</a></li>
+ <li><a href="#c_determine_the_device_your_instance_is_running_on">Determine the
+device your instance is running on</a></li>
+ <li><a href="#d_create_a_unique_identifier_for_advertising_or_user_analytics">
+Create a unique identifier for advertising or user analytics</a></li>
+ </ol>
+ </li>
+ <li><a href="#know_the_libraries_you're_working_with">Know the Libraries You're
+Working With</a></li>
+ <li><a href="#be_transparent">Be Transparent</a></li>
+ </ol>
+ <h2>You should also read</h2>
+ <ol>
+ <li><a href="{@docRoot}guide/topics/security/permissions.html">System Permissions</a></li>
+ <li><a href="{@docRoot}training/permissions/index.html">Working with System
+ Permissions</a></li>
+ </ol>
+ </div>
+</div>
+
+<p>
+ Permission requests protect sensitive information available from a device and
+ should only be used when access to information is necessary for the
+ functioning of your app. This document provides tips on ways you might be
+ able to achieve the same (or better) functionality without requiring access
+ to such information; it is not an exhaustive discussion of how permissions
+ work in the Android operating system.
+</p>
+
+<p>
+ For a more general look at Android permissions, please see <a href=
+ "{@docRoot}training/articles/user-data-overview.html">Permissions
+ and User Privacy</a>. For details on how to work with permissions in your code,
+ see <a href="{@docRoot}training/permissions/index.html">Working with System Permissions</a>.
+ For best practices for working with unique identifiers, please see <a href=
+ "{@docRoot}training/articles/user-data-ids.html">Best Practices for
+ Unique Identifiers</a>.
+</p>
+
+<h2 id="tenets_of_working_with_android_permissions">Tenets of Working
+with Android Permissions</h2>
+
+<p>
+ We recommend following these tenets when working with Android permissions:
+</p>
+
+<p>
+ <em><strong>#1: Only use the permissions necessary for your app to
+ work</strong></em>. Depending on how you are using the permissions, there may
+ be another way to do what you need (system intents, identifiers,
+ backgrounding for phone calls) without relying on access to sensitive
+ information.
+</p>
+
+<p>
+ <em><strong>#2: Pay attention to permissions required by
+ libraries.</strong></em> When you include a library, you also inherit its
+ permission requirements. You should be aware of what you're including, the
+ permissions they require, and what those permissions are used for.
+</p>
+
+<p>
+ <em><strong>#3: Be transparent.</strong></em> When you make a permissions
+ request, be clear about what you’re accessing, and why, so users can make
+ informed decisions. Make this information available alongside the permission
+ request including install, runtime, or update permission dialogues.
+</p>
+
+<p>
+ <em><strong>#4: Make system accesses explicit.</strong></em> Providing
+ continuous indications when you access sensitive capabilities (for example, the
+ camera or microphone) makes it clear to users when you’re collecting data and
+ avoids the perception that you're collecting data surreptitiously.
+</p>
+
+<p>
+ The remaining sections of this guide elaborate on these rules in the context
+ of developing Android applications.
+</p>
+
+<h2 id="version_specific_details_permissions_in_m">Permissions in Android 6.0+</h2>
+
+<p>
+ Android 6.0 Marshmallow introduced a <a href=
+ "{@docRoot}training/permissions/requesting.html">new permissions model</a> that
+ lets apps request permissions from the user at runtime, rather than prior to
+ installation. Apps that support the new model request permissions when the app
+ actually requires the services or data protected by the services. While this
+ doesn't (necessarily) change overall app behavior, it does create a few
+ changes relevant to the way sensitive user data is handled:
+</p>
+
+<p>
+ <em><strong>Increased situational context</strong></em>: Users are be
+ prompted at runtime, in the context of your app, for permission to access the
+ functionality covered by those permission groups. Users are be more sensitive to
+ the context in which the permission is requested, and if there’s a mismatch
+ between what you are requesting and the purpose of your app, it's even
+ more important to provide detailed explanation to the user as to why you’re
+ requesting the permission; whenever possible, you should provide an
+ explanation of your request both at the time of the request and in a
+ follow-up dialog if the user denies the request.
+</p>
+
+<p>
+ <em><strong>Greater flexibility in granting permissions</strong></em>: Users
+ can deny access to individual permissions at the time they’re requested
+ <em>and</em> in settings, but they may still be surprised when functionality is
+ broken as a result. It’s a good idea to monitor how many users are denying
+ permissions (e.g. using Google Analytics) so that you can either refactor
+ your app to avoid depending on that permission or provide a better
+ explanation of why you need the permission for your app to work properly. You
+ should also make sure that your app handles exceptions created when users
+ deny permission requests or toggle off permissions in settings.
+</p>
+
+<p>
+ <em><strong>Increased transactional burden</strong></em>: Users will be asked
+ to grant access for permission groups individually and not as a set. This
+ makes it extremely important to minimize the number of permissions you’re
+ requesting because it increases the user burden for granting permissions and
+ increases the probability that at least one of the requests will be denied.
+</p>
+
+<h2 id="avoid_requesting_unnecessary_permissions">Avoid Requesting
+Unnecessary Permissions</h2>
+
+<p>
+ This section provides alternatives to common use-cases that will help you
+ limit the number of permission requests you make. Since the number and type
+ of user-surfaced permissions requested affects downloads compared to other
+ similar apps requesting fewer permissions, it’s best to avoid requesting
+ permissions for unnecessary functionality.
+</p>
+
+<h3 id="a_camera_contact_access_with_real-time_user_requests">Camera/contact
+access with realtime user requests</h3>
+
+<p>
+ <em>In this case, you need occasional access to the device's camera or
+ contact information and don’t mind the user being asked every time you need
+ access.</em>
+</p>
+
+<p>
+ If your requirement for access to user data is infrequent — in other
+ words, it's not unacceptably disruptive for the user to be presented with a
+ runtime dialogue each time you need to access data — you can use an
+ <em>intent based request</em>. Android provides system intents that
+ applications can use without requiring permissions because the user chooses
+ what, if anything, to share with the app at the time the intent based request
+ is issued.
+</p>
+
+<p>
+ For example, an intent action type of <code><a href=
+ "{@docRoot}reference/android/provider/MediaStore.html#ACTION_IMAGE_CAPTURE">MediaStore.ACTION_IMAGE_CAPTURE</a></code>
+ or <code><a href=
+ "{@docRoot}reference/android/provider/MediaStore.html#ACTION_VIDEO_CAPTURE">MediaStore.ACTION_VIDEO_CAPTURE</a></code>
+ can be used to capture images or videos without directly using the <a href=
+ "{@docRoot}reference/android/hardware/Camera.html">Camera</a> object (or
+ requiring the permission). In this case, the system intent will ask for the
+ user’s permission on your behalf every time an image is captured.
+</p>
+
+<h3 id="b_running_in_the_background_after_losing_audio_focus">Running in
+the background after losing audio focus</h3>
+
+<p>
+ <em>In this case, your application needs to go into the background when the
+ user gets a phone call and refocus only once the call stops.</em>
+</p>
+
+<p>
+ The common approach in these cases - for example, a media player muting or
+ pausing during a phone call - is to listen for changes in the call state
+ using <code>PhoneStateListener</code> or listening for the broadcast of
+ <code>android.intent.action.PHONE_STATE</code>. The problem with this
+ solution is that it requires the <code>READ_PHONE_STATE</code> permission,
+ which forces the user to grant access to a wide cross section of sensitive
+ data such as their device and SIM hardware IDs and the phone number of the
+ incoming call.
+</p>
+
+<p>
+ You can avoid this by requesting <code>AudioFocus</code> for your app, which
+ doesn't require explicit permissions (because it does not access sensitive
+ information). Simply put the code required to background your audio in the
+ <code><a href=
+ "{@docRoot}reference/android/media/AudioManager.OnAudioFocusChangeListener.html#onAudioFocusChange(int)">
+ onAudioFocusChange()</a></code> event handler and it will run automatically
+ when the OS shifts its audio focus. More detailed documentation on how to do
+ this can be found <a href=
+ "{@docRoot}training/managing-audio/audio-focus.html">here</a>.
+</p>
+
+<h3 id="c_determine_the_device_your_instance_is_running_on">Determine the
+device your instance is running on</h3>
+
+<p>
+ <em>In this case, you need a unique identifier to determine which device the
+ instance of your app is running on.</em>
+</p>
+
+<p>
+ Applications may have device-specific preferences or messaging (e.g., saving
+ a device-specific playlist for a user in the cloud so that they can have a
+ different playlist for their car and at home). A common solution is to
+ leverage device identifiers such as <code>Device IMEI</code>, but this
+ requires the <code>Device ID and call information</code>
+ permission group (<code>PHONE</code> in M+). It also uses an identifier which
+ cannot be reset and is shared across all apps.
+</p>
+
+<p>
+ There are two alternatives to using these types of identifiers:
+</p>
+
+<ol>
+ <li> Use the <code>com.google.android.gms.iid</code> InstanceID API.
+ <code>getInstance(Context context).getID()<strong></code> </strong>will return a
+ unique device identifier for your application instance. The
+result is an app instance scoped identifier that can be used as a key when
+storing information about the app and is reset if the user re-installs the app.
+ <li> Create your own identifier that’s scoped to your app’s storage using basic
+ system functions like <a
+ href="{@docRoot}reference/java/util/UUID.html#randomUUID()"><code>randomUUID()</code></a>.</li>
+</ol>
+
+<h3 id="d_create_a_unique_identifier_for_advertising_or_user_analytics">Create a unique
+identifier for advertising or user analytics</h3>
+
+<p>
+ <em>In this case, you need a unique identifier for building a profile for
+ users who are not signed in to your app (e.g., for ads targeting or measuring
+ conversions).</em>
+</p>
+
+<p>
+ Building a profile for advertising and user analytics sometimes requires an
+ identifier that is shared across other applications. Common solutions for
+ this involve leveraging device identifiers such as <code>Device IMEI</code>,
+ which requires the <code>Device ID</code> <code>and call information</code>
+ permission group (<code>PHONE</code> in API level 23+) and cannot be reset by
+ the user. In any of these cases, in addition to using a non-resettable
+ identifier and requesting a permission that might seem unusual to users, you
+ will also be in violation of the <a href=
+ "https://play.google.com/about/developer-content-policy.html">Play Developer
+ Program Policies</a>.
+</p>
+
+<p>
+ Unfortunately, in these cases using the
+ <code>com.google.android.gms.iid</code> InstanceID API or system functions to
+ create an app-scoped ID are not appropriate solutions because the ID may need
+ to be shared across apps. An alternative solution is to use the
+ <code>Advertising Identifier</code> available from the <code><a href=
+ "{@docRoot}reference/com/google/android/gms/ads/identifier/AdvertisingIdClient.Info.html">
+ AdvertisingIdClient.Info</a></code> class via the <code>getId()</code>
+ method. You can create an <code>AdvertisingIdClient.Info</code> object using
+ the <code>getAdvertisingIdInfo(Context)</code> method and call the
+ <code>getId()</code> method to use the identifier. <em><strong>Note that this
+ method is blocking</strong></em>, so you should not call it from the main
+ thread; a detailed explanation of this method is available <a href=
+ "{@docRoot}google/play-services/id.html">here</a>.
+</p>
+
+<h2 id="know_the_libraries_you're_working_with">Know the Libraries You're
+Working With</h2>
+
+<p>
+ Sometimes permissions are required by the libraries you use in your app. For
+ example, ads and analytics libraries may require access to the
+ <code>Location</code> or <code>Identity</code> permissions groups to
+ implement the required functionality. But from the user’s point of view, the
+ permission request comes from your app, not the library.
+</p>
+
+<p>
+ Just as users select apps that use fewer permissions for the same
+ functionality, developers should review their libraries and select
+ third-party SDKs that are not using unnecessary permissions. For example, try
+ to avoid libraries that require the <code>Identity</code> permission group
+ unless there is a clear user-facing reason why the app needs those permissions.
+ In particular, for libraries that provide location functionality, make sure you
+ are not required to request the <code>FINE_LOCATION</code> permission unless
+ you are using location-based targeting functionality.
+</p>
+
+<h2 id="be_transparent">Be Transparent</h2>
+
+<p>You should inform your users about what you’re accessing and why. Research shows
+that users are much less uncomfortable with permissions requests if they know
+why the app needs them. A user study showed that:</p>
+
+<div style="padding:.5em 2em;">
+<div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
+<p>...a user’s willingness to grant a given permission to a given mobile app is
+strongly influenced by the purpose associated with such a permission. For
+instance a user’s willingness to grant access to his or her location will vary
+based on whether the request is required to support the app’s core
+functionality or whether it is to share this information with an advertising
+network or an analytics company.<span
+style="font-size:.8em;color:#777"><sup><em><a
+ href="#references" style="color:#777;padding-left:.1em;">1</a></em></sup></span></p>
+</div>
+</div>
+
+<p>
+ Based on his group’s research, Professor Jason Hong from CMU concluded that,
+ in general:
+</p>
+
+<div style="padding:.5em 2em;">
+<div style="border-left:4px solid #999;padding:0 1em;font-style:italic;">
+<p>...when people know why an app is using something as sensitive as their location —
+for example, for targeted advertising — it makes them more comfortable than
+when simply told an app is using their location.<span
+style="font-size:.8em;color:#777"><sup><em><a
+ href="#references" style="color:#777;padding-left:.1em;">1</a></em></sup></span></p>
+</div>
+</div>
+
+<p>
+ As a result, if you’re only using a fraction of the API calls that fall under
+ a permission group, it helps to explicitly list which of those permissions
+ you're using, and why. For example:
+</p>
+
+<ul>
+ <li> If you’re only using coarse location, let the user know this in your app
+ description or in help articles about your app. </li>
+ <li> If you need access to SMS messages to receive authentication codes that
+ protect the user from fraud, let the user know this in your app description
+ and/or the first time you access the data.</li>
+</ul>
+
+<p>
+ Under certain conditions, it's also advantageous to let users know about
+ sensitive data accesses in real-time. For example, if you’re accessing the
+ camera or microphone, it’s usually a good idea to let the user know with a
+ notification icon somewhere in your app, or in the notification tray (if the
+ application is running in the background), so it doesn't seem like you're
+ collecting data surreptitiously.
+</p>
+
+<p>
+ Ultimately, if you need to request a permission to make something in your app
+ work, but the reason is not clear to the user, find a way to let the user
+ know why you need the most sensitive permissions.
+</p>
+
+<h2 id="references">References</h2>
+
+<p>
+ [1] <em>Modeling Users’ Mobile App Privacy Preferences: Restoring Usability
+ in a Sea of Permission Settings</em>, by J. Lin B. Liu, N. Sadeh and J. Hong.
+ In Proceedings of SOUPS 2014.
+</p>
diff --git a/docs/html/training/best-permissions-ids.jd b/docs/html/training/best-permissions-ids.jd
new file mode 100644
index 0000000..e98c095
--- /dev/null
+++ b/docs/html/training/best-permissions-ids.jd
@@ -0,0 +1,9 @@
+page.title=Best Practices for Permissions and Identifiers
+page.trainingcourse=true
+
+@jd:body
+
+
+
+<p>The articles below highlight key guidelines for using permissions
+and identifiers properly in your apps.</p>
\ No newline at end of file
diff --git a/docs/html/training/training_toc.cs b/docs/html/training/training_toc.cs
index 9e156d0..5ebb298 100644
--- a/docs/html/training/training_toc.cs
+++ b/docs/html/training/training_toc.cs
@@ -2085,6 +2085,36 @@
<li class="nav-section">
<div class="nav-section-header">
+ <a href="<?cs var:toroot ?>training/best-permissions-ids.html">
+ <span class="small">Best Practices for</span><br/>
+ Permissions & Identifiers
+ </a>
+ </div>
+ <ul>
+ <li>
+ <a href="<?cs var:toroot ?>training/articles/user-data-overview.html"
+ description=
+ "Overview of app permissions on Android and how they affect your users."
+ >Permissions and User Privacy</a>
+ </li>
+ <li>
+ <a href="<?cs var:toroot ?>training/articles/user-data-permissions.html"
+ description=
+ "How to manage permissions the right way for users."
+ >Best Practices for App Permissions</a>
+ </li>
+ <li>
+ <a href="<?cs var:toroot ?>training/articles/user-data-ids.html"
+ description=
+ "Unique identifiers available and how to choose the right one for your use case."
+ >Best Practices for Unique Identifiers</a>
+ </li>
+ </ul>
+ </li>
+ <!-- End Permissions and identifiers -->
+
+ <li class="nav-section">
+ <div class="nav-section-header">
<a href="<?cs var:toroot ?>training/testing.html">
<span class="small">Best Practices for</span><br/>
Testing