how to know what resources an android studio program has access to

This developer's guide explains how your device policy controller (DPC) tin manage multiple Android users on dedicated devices.

Overview

Your DPC can help multiple people share a unmarried defended device. Your DPC running on a fully managed device can create and manage two types of users:

  • Secondary users are Android users with separate apps and data saved between sessions. You manage the user with an admin component. These users are useful for cases where a device is picked up at the starting time of a shift, such every bit delivery drivers or security workers.
  • Ephemeral users are secondary users that the system deletes when the user stops, switches away, or the device reboots. These users are useful for cases where data can be deleted after the session finishes, such as public-access internet kiosks.

Y'all utilise your existing DPC to manage the dedicated device and the secondary users. An admin component in your DPC sets itself equally the admin for new secondary users when you create them.

Primary user and two secondary users.
Effigy one. Primary and secondary users managed by admins from the same DPC

Admins of a secondary user must vest to the same package as the admin of the fully managed device. To simplify development, nosotros recommend sharing an admin between the device and secondary users.

Managing multiple users on dedicated devices typically requires Android 9.0, even so some of the methods used in this programmer'due south guide are available in before versions of Android.

Create users

Your DPC can create additional users in the groundwork and then can switch them to the foreground. The process is almost the same for both secondary and ephemeral users. Implement the following steps in the admins of the fully managed device and secondary user:

  1. Call DevicePolicyManager.createAndManageUser(). To create an ephemeral user, include MAKE_USER_EPHEMERAL in the flags argument.
  2. Call DevicePolicyManager.startUserInBackground() to get-go the user in the background. The user starts running but yous will want to finish setup before bringing the user to the foreground and showing it to the person using the device.
  3. In the admin of the secondary user, call DevicePolicyManager.setAffiliationIds() to chapter the new user with the main user. Encounter DPC coordination below.
  4. Dorsum in the admin of the fully managed device, call DevicePolicyManager.switchUser() to switch the user to the foreground.

The post-obit sample shows how you can add together stride 1 to your DPC:

Kotlin

val dpm = getContext().getSystemService(Context.DEVICE_POLICY_SERVICE)         as DevicePolicyManager  // If possible, reuse an existing affiliation ID across the // master user and (subsequently) the ephemeral user. val identifiers = dpm.getAffiliationIds(adminName) if (identifiers.isEmpty()) {     identifiers.add(UUID.randomUUID().toString())     dpm.setAffiliationIds(adminName, identifiers) }  // Pass an amalgamation ID to the ephemeral user in the admin extras. val adminExtras = PersistableBundle() adminExtras.putString(AFFILIATION_ID_KEY, identifiers.first()) // Include whatsoever other config for the new user here ...  // Create the ephemeral user, using this component equally the admin. try {     val ephemeralUser = dpm.createAndManageUser(             adminName,             "tmp_user",             adminName,             adminExtras,             DevicePolicyManager.MAKE_USER_EPHEMERAL or                     DevicePolicyManager.SKIP_SETUP_WIZARD)  } catch (e: UserManager.UserOperationException) {     if (e.userOperationResult ==             UserManager.USER_OPERATION_ERROR_MAX_USERS) {         // Detect a mode to free up users...     } }

Java

DevicePolicyManager dpm = (DevicePolicyManager)     getContext().getSystemService(Context.DEVICE_POLICY_SERVICE);  // If possible, reuse an existing affiliation ID across the // primary user and (after) the imperceptible user. Set<String> identifiers = dpm.getAffiliationIds(adminName); if (identifiers.isEmpty()) {   identifiers.add together(UUID.randomUUID().toString());   dpm.setAffiliationIds(adminName, identifiers); }  // Pass an affiliation ID to the ephemeral user in the admin extras. PersistableBundle adminExtras = new PersistableBundle(); adminExtras.putString(AFFILIATION_ID_KEY, identifiers.iterator().side by side()); // Include whatsoever other config for the new user here ...  // Create the ephemeral user, using this component as the admin. try {   UserHandle ephemeralUser = dpm.createAndManageUser(       adminName,       "tmp_user",       adminName,       adminExtras,       DevicePolicyManager.MAKE_USER_EPHEMERAL |           DevicePolicyManager.SKIP_SETUP_WIZARD);  } catch (UserManager.UserOperationException e) {   if (e.getUserOperationResult() ==       UserManager.USER_OPERATION_ERROR_MAX_USERS) {     // Observe a way to free up users...   } }

When y'all create or outset a new user, you tin can check the reason for any failures by catching the UserOperationException exception and calling getUserOperationResult(). Exceeding the user limits are common failure reasons:

  • USER_OPERATION_ERROR_MAX_USERS
  • USER_OPERATION_ERROR_MAX_RUNNING_USERS

Creating a user can take some time. If y'all're frequently creating users, you can improve the user experience by preparing a set up-to-go user in the background. You might demand to balance the advantages of a ready-to-go user with the maximum number of users allowed on a device.

Identification

After creating a new user, yous should refer to the user with a persistent series number. Don't persist the UserHandle because the organisation recycles these equally you create and delete users. Get the serial number by calling UserManager.getSerialNumberForUser():

Kotlin

// Afterward calling createAndManageUser() use a device-unique series number // (that isn't recycled) to identify the new user. secondaryUser?.let {     val userManager = getContext().getSystemService(UserManager::class.coffee)     val ephemeralUserId = userManager!!.getSerialNumberForUser(it)     // Save the series number to storage  ... }

Java

// Afterwards calling createAndManageUser() use a device-unique series number // (that isn't recycled) to identify the new user. if (secondaryUser != null) {   UserManager userManager = getContext().getSystemService(UserManager.course);   long ephemeralUserId = userManager.getSerialNumberForUser(secondaryUser);   // Save the serial number to storage  ... }

User config

Depending on the needs of your users, y'all can customize the setup of secondary users. You tin can include the following flags when calling createAndManageUser():

SKIP_SETUP_WIZARD
Skips running the new-user setup magician that checks for and installs updates, prompts the user to add a Google Account along with Google services, and sets a screen lock. This can take some time and might not be applicable for all users—public internet kiosks, for example.
LEAVE_ALL_SYSTEM_APPS_ENABLED
Leaves all the arrangement apps enabled in the new user. If yous don't set this flag, the new user contains simply the minimal set of apps that the telephone needs to operate—typically a file browser, phone dialer, contacts, and SMS messages.

Follow the user lifecycle

Your DPC (if information technology'southward an admin of the fully managed device) might find information technology useful to know when secondary users change. To run follow-on tasks subsequently changes, override these callback methods in your DPC'southward DeviceAdminReceiver subclass:

onUserStarted()
Called later the system starts a user. This user might nevertheless exist setting upwards or exist running in the background. You can get the user from the startedUser argument.
onUserSwitched()
Chosen after the organization switches to a different user. You can get the new user that's now running in the foreground from the switchedUser argument.
onUserStopped()
Chosen after the system stops a user because they logged out, switched to a new user (if the user is ephemeral), or your DPC stopped the user. You can get the user from the stoppedUser statement.
onUserAdded()
Called when the organization adds a new user. Typically, secondary users aren't fully set up when your DPC gets the callback. Yous can get the user from the newUser argument.
onUserRemoved()
Called after the organisation deletes a user. Considering the user is already deleted, you can't access the user represented by the removedUser argument.

To know when the system brings a user to the foreground or sends a user to the background, apps tin annals a receiver for the ACTION_USER_FOREGROUND and ACTION_USER_BACKGROUND broadcasts.

Discover users

To get all the secondary users, an admin of a fully managed device can call DevicePolicyManager.getSecondaryUsers(). The results include whatsoever secondary or ephemeral users the admin created. The results also include any secondary users (or a guest user) a person using the device might have created. The results don't include work profiles because they aren't secondary users. The following sample shows how yous can use this method:

Kotlin

// The device is stored for the night. Stop all running secondary users. dpm.getSecondaryUsers(adminName).forEach {     dpm.stopUser(adminName, it) }

Java

// The device is stored for the night. Stop all running secondary users. for (UserHandle user : dpm.getSecondaryUsers(adminName)) {   dpm.stopUser(adminName, user); }

Here are other methods you tin call to detect out the status of secondary users:

DevicePolicyManager.isEphemeralUser()
Phone call this method from the admin of a secondary user to detect out if this is an ephemeral user.
DevicePolicyManager.isAffiliatedUser()
Call this method from the admin of a secondary user to detect out if this user is affiliated with the master user. To learn more about amalgamation, meet DPC coordination below.

User management

If you want to completely manage the user lifecycle, y'all tin call APIs for fine-grained control of when and how the device changes users. For example, yous can delete a user when a device hasn't been used for a period of time or you can send any unsent orders to a server before a person'due south shift finishes.

Logout

Android 9.0 added a log-out push to the lock screen and so that a person using the device can end their session. After tapping the push, the system stops the secondary user, deletes the user if it's ephemeral, and the primary user returns to the foreground. Android hides the button when the chief user is in the foreground because the primary user can't log out.

Android doesn't testify the end-session push button past default but your admin (of a fully managed device) tin enable it past calling DevicePolicyManager.setLogoutEnabled(). If yous need to confirm the electric current state of the button, phone call DevicePolicyManager.isLogoutEnabled().

The admin of a secondary user can programmatically log out the user and render to the main user. Showtime, confirm the secondary and the master users are affiliated, then call DevicePolicyManager.logoutUser(). If the logged-out user is an ephemeral user, the system stops and then deletes the user.

Switch users

To switch to a unlike secondary user, the admin of a fully managed device tin can call DevicePolicyManager.switchUser(). Equally a convenience, you can pass null to switch to the primary user.

Stop a user

To end a secondary user, a DPC that owns a fully managed device can call DevicePolicyManager.stopUser(). If the stopped user is an ephemeral user, the user is stopped and so deleted.

We recommend stopping users whenever possible to assist stay below the device'south maximum number of running users.

Delete a user

To permanently delete a secondary user a DPC tin can telephone call one of the following DevicePolicyManager methods:

  • An admin of a fully managed device tin can telephone call removeUser().
  • An admin of the secondary user tin phone call wipeData().

The system deletes ephemeral users when they're logged out, stopped, or switched abroad from.

Disable the default UI

If your DPC provides a UI to manage users, you can disable Android's congenital-in multi-user interface. You tin do this by calling DevicePolicyManager.setLogoutEnabled() and adding the DISALLOW_USER_SWITCH restriction as shown in the following example:

Kotlin

// Explicitly disallow logging out using Android UI (disabled by default). dpm.setLogoutEnabled(adminName, false)  // Disallow switching users in Android's UI. This DPC tin yet // telephone call switchUser() to manage users. dpm.addUserRestriction(adminName, UserManager.DISALLOW_USER_SWITCH)

Java

// Explicitly disallow logging out using Android UI (disabled past default). dpm.setLogoutEnabled(adminName, fake);  // Disallow switching users in Android'due south UI. This DPC tin can however // phone call switchUser() to manage users. dpm.addUserRestriction(adminName, UserManager.DISALLOW_USER_SWITCH);

The person using the device tin't add together secondary users with Android'southward congenital-in UI considering admins of fully managed devices automatically add together the DISALLOW_ADD_USER user restriction.

Session messages

When the person using a device switches to a new user, Android shows a panel to highlight the switch. Android shows the following messages:

  • Start-user-session message shown when the device switches to a secondary user from the primary user.
  • Cease-user-session bulletin shown when the device returns to the primary user from a secondary user.

The system doesn't prove the messages when switching between ii secondary users.

Because the messages might non be suitable for all situations, you can change the text of these messages. For instance, if your solution uses ephemeral user sessions, you tin can reverberate this in the messages such as: Stopping browser session & deleting personal data…

The system shows the message for merely a couple of seconds, and so each message should be a curt, clear phrase. To customize the messages, your admin tin call the DevicePolicyManager methods setStartUserSessionMessage() and setEndUserSessionMessage() as shown in the following instance:

Kotlin

// Curt, easy-to-read messages shown at the start and end of a session. // In your app, store these strings in a localizable resource. internal val START_USER_SESSION_MESSAGE = "Starting guest session…" internal val END_USER_SESSION_MESSAGE = "Stopping & clearing data…"  // ... dpm.setStartUserSessionMessage(adminName, START_USER_SESSION_MESSAGE) dpm.setEndUserSessionMessage(adminName, END_USER_SESSION_MESSAGE)

Java

// Short, piece of cake-to-read messages shown at the start and end of a session. // In your app, shop these strings in a localizable resource. private static final String START_USER_SESSION_MESSAGE = "Starting guest session…"; individual static terminal Cord END_USER_SESSION_MESSAGE = "Stopping & clearing data…";  // ... dpm.setStartUserSessionMessage(adminName, START_USER_SESSION_MESSAGE); dpm.setEndUserSessionMessage(adminName, END_USER_SESSION_MESSAGE);

Laissez passer nada to delete your custom messages and return to Android's default messages. If you need to cheque the current bulletin text, call getStartUserSessionMessage() or getEndUserSessionMessage().

Your DPC should gear up localized messages for the user's current locale. You as well demand to update the messages when the user's locale changes:

Kotlin

override fun onReceive(context: Context?, intent: Intent?) {     // Added the <action android:name="android.intent.action.LOCALE_CHANGED" />     // intent filter for our DeviceAdminReceiver subclass in the app manifest file.     if (intent?.action === ACTION_LOCALE_CHANGED) {          // Android's resources return a string suitable for the new locale.         getManager(context).setStartUserSessionMessage(                 getWho(context),                 context?.getString(R.cord.start_user_session_message))          getManager(context).setEndUserSessionMessage(                 getWho(context),                 context?.getString(R.string.end_user_session_message))     }     super.onReceive(context, intent) }

Java

public void onReceive(Context context, Intent intent) {   // Added the <action android:proper name="android.intent.activeness.LOCALE_CHANGED" />   // intent filter for our DeviceAdminReceiver subclass in the app manifest file.   if (intent.getAction().equals(ACTION_LOCALE_CHANGED)) {      // Android'due south resource render a string suitable for the new locale.     getManager(context).setStartUserSessionMessage(         getWho(context),         context.getString(R.string.start_user_session_message));      getManager(context).setEndUserSessionMessage(         getWho(context),         context.getString(R.string.end_user_session_message));   }   super.onReceive(context, intent); }

DPC coordination

Managing secondary users typically needs two instances of your DPC—i that owns the fully managed device while the other owns the secondary user. When creating a new user, the admin of the fully managed device sets some other instance of itself as the admin of the new user.

Affiliated users

Some of the APIs in this developer's guide only work when the secondary users are affiliated. Because Android disables some features (network logging for example) when you add new unaffiliated secondary users to the device, you should affiliate users as soon as possible. Run into the case in Setup beneath.

Setup

Set up new secondary users (from the DPC that owns the secondary user) earlier letting people employ them. You can do this setup from the DeviceAdminReceiver.onEnabled() callback. If you previously set any admin extras in the telephone call to createAndManageUser(), y'all can get the values from the intent argument. The following example shows a DPC affiliating a new secondary user in the callback:

Kotlin

override fun onEnabled(context: Context?, intent: Intent?) {     super.onEnabled(context, intent)      // Get the affiliation ID (our DPC previously put in the extras) and     // set the ID for this new secondary user.     intent?.getStringExtra(AFFILIATION_ID_KEY)?.let {         val dpm = getManager(context)         dpm.setAffiliationIds(getWho(context), setOf(information technology))     }     // Continue setup of the new secondary user ... }

Java

public void onEnabled(Context context, Intent intent) {   // Get the affiliation ID (our DPC previously put in the extras) and   // set the ID for this new secondary user.   String affiliationId = intent.getStringExtra(AFFILIATION_ID_KEY);   if (affiliationId != zippo) {     DevicePolicyManager dpm = getManager(context);     dpm.setAffiliationIds(getWho(context),         new HashSet<String>(Arrays.asList(affiliationId)));   }   // Proceed setup of the new secondary user ... }

RPCs betwixt DPCs

Even though the two DPC instances are running nether split up users, the DPCs that ain the device and the secondary users can communicate with each other. Considering calling another DPC's service crosses user boundaries, your DPC can't call bindService() equally you normally would in Android. To bind to a service running in another user, phone call DevicePolicyManager.bindDeviceAdminServiceAsUser().

Primary user and two affiliated secondary users calling RPCs.
Figure 2. Admins of affiliated master and secondary users calling service methods

Your DPC can just bind to services running in the users returned past DevicePolicyManager.getBindDeviceAdminTargetUsers(). The post-obit case shows the admin of a secondary user binding to the admin of the fully managed device:

Kotlin

// From a secondary user, the list contains simply the primary user. dpm.getBindDeviceAdminTargetUsers(adminName).forEach {      // Set up the callbacks for the service connectedness.     val intent = Intent(mContext, FullyManagedDeviceService::form.java)     val serviceconnection = object : ServiceConnection {         override fun onServiceConnected(componentName: ComponentName,                                         iBinder: IBinder) {             // Phone call methods on service ...         }         override fun onServiceDisconnected(componentName: ComponentName) {             // Clean up or reconnect if needed ...         }     }      // Bind to the service as the primary user [information technology].     val bindSuccessful = dpm.bindDeviceAdminServiceAsUser(adminName,             intent,             serviceconnection,             Context.BIND_AUTO_CREATE,             it) }

Coffee

// From a secondary user, the list contains merely the primary user. List<UserHandle> targetUsers = dpm.getBindDeviceAdminTargetUsers(adminName); if (targetUsers.isEmpty()) {   // If the users aren't affiliated, the listing doesn't incorporate any users.   return; }  // Prepare the callbacks for the service connectedness. Intent intent = new Intent(mContext, FullyManagedDeviceService.form); ServiceConnection serviceconnection = new ServiceConnection() {   @Override   public void onServiceConnected(       ComponentName componentName, IBinder iBinder) {     // Call methods on service ...   }    @Override   public void onServiceDisconnected(ComponentName componentName) {     // Clean up or reconnect if needed ...   } };  // Demark to the service as the primary user. UserHandle primaryUser = targetUsers.go(0); boolean bindSuccessful = dpm.bindDeviceAdminServiceAsUser(     adminName,     intent,     serviceconnection,     Context.BIND_AUTO_CREATE,     primaryUser);

To learn more, including providing a service that other users can demark to, read Profile communication.

Additional resources

To acquire more about dedicated devices, read the following documents:

  • Dedicated devices overview is an overview of dedicated devices.
  • Lock task mode explains how to lock a defended device to a single app or gear up of apps.
  • Dedicated devices cookbook with further examples to restrict the dedicated devices and enhance the user experience.

cooperthatimetat.blogspot.com

Source: https://developer.android.com/work/dpc/dedicated-devices/multiple-users

0 Response to "how to know what resources an android studio program has access to"

Post a Comment

Iklan Atas Artikel

Iklan Tengah Artikel 1

Iklan Tengah Artikel 2

Iklan Bawah Artikel