Z tego przewodnika dla programistów dowiesz się, jak kontroler zasad dotyczących urządzeń może zarządzać wieloma użytkownikami Androida na specjalnych urządzeniach.
Omówienie
Twój DPC może pomóc wielu osobom korzystać z jednego specjalnego urządzenia. Twój DPC działające na w pełni zarządzanym urządzeniu może tworzyć 2 typy użytkowników i nimi zarządzać:
- Użytkownicy dodatkowi to użytkownicy Androida, którzy mają zapisane osobne aplikacje i dane między sesjami. Do zarządzania użytkownikiem służy komponent administratora. Ci użytkownicy są przydatne w przypadkach, gdy urządzenie zostanie odebrane na początku zmiany, na przykład dostawcom czy ochroniarzom.
- Użytkownicy efemeryczni to użytkownicy pomocniczy, którzy są usuwani przez system, gdy użytkownik zatrzymuje się, wyłącza lub urządzenie uruchamia się ponownie. Ci użytkownicy przydają się w przypadkach, gdzie po zakończeniu sesji można usunąć dane, np. dostęp publiczny. kiosków internetowych.
Do zarządzania oddzielnym i dodatkowym urządzeniem możesz używać obecnej wersji DPC. użytkowników. Komponent administracyjny w DPC ustawia się jako administrator nowej dodatkowej usługi użytkowników podczas ich tworzenia.
.Administratorzy użytkownika dodatkowego muszą należeć do tego samego pakietu co administrator w pełni zarządzane urządzenie. Aby uprościć programowanie, zalecamy udostępnienie informacji o administratorze między urządzeniem a użytkownikami pomocniczymi.
Zarządzanie wieloma użytkownikami na specjalnych urządzeniach zwykle wymaga Androida 9.0, ale niektóre metody omówione w tym przewodniku dla programistów są dostępne starszych wersji Androida.
Użytkownicy dodatkowi
Użytkownicy dodatkowi mogą łączyć się z Wi-Fi i konfigurować nowe sieci. Jednak są one Nie mogą edytować ani usuwać sieci, nawet tych, które utworzyły.
Tworzenie użytkowników
DPC może utworzyć w tle dodatkowych użytkowników, a następnie ich przełączyć na pierwszy plan. Proces ten jest niemal taki sam zarówno w przypadku efemeryczną. Te kroki należy wdrożyć u administratorów w pełni urządzenie zarządzane i użytkownik dodatkowy:
- Zadzwoń pod numer
DevicePolicyManager.createAndManageUser()
. Aby utworzyć użytkownika tymczasowego, dołączMAKE_USER_EPHEMERAL
w argumencie flag. - Zadzwoń do nas
DevicePolicyManager.startUserInBackground()
do uruchamia użytkownika w tle. Użytkownik zaczyna działać, ale chcesz aby dokończyć konfigurację, zanim przeniesiesz użytkownika na pierwszy plan i wyświetlisz go do osoby korzystającej z urządzenia. - Na koncie administratora użytkownika dodatkowego wywołaj
DevicePolicyManager.setAffiliationIds()
do powiąż nowego użytkownika z użytkownikiem głównym. Zobacz Koordynacja DPC poniżej. - Wróć do konta administratora w pełni zarządzanego urządzenia i zadzwoń
DevicePolicyManager.switchUser()
, aby przełączyć użytkownika na: na pierwszym planie.
Z przykładu poniżej dowiesz się, jak dodać krok 1 do DPC:
Kotlin
val dpm = getContext().getSystemService(Context.DEVICE_POLICY_SERVICE) as DevicePolicyManager // If possible, reuse an existing affiliation ID across the // primary user and (later) the ephemeral user. val identifiers = dpm.getAffiliationIds(adminName) if (identifiers.isEmpty()) { identifiers.add(UUID.randomUUID().toString()) dpm.setAffiliationIds(adminName, identifiers) } // Pass an affiliation ID to the ephemeral user in the admin extras. val adminExtras = PersistableBundle() adminExtras.putString(AFFILIATION_ID_KEY, identifiers.first()) // Include any other config for the new user here ... // Create the ephemeral user, using this component as 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) { // Find a way 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 (later) the ephemeral user. Set<String> identifiers = dpm.getAffiliationIds(adminName); if (identifiers.isEmpty()) { identifiers.add(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().next()); // Include any 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) { // Find a way to free up users... } }
Podczas tworzenia lub uruchamiania nowego konta użytkownika możesz sprawdzić przyczynę niepowodzenia
przechwytując wyjątek UserOperationException
i wywołując
getUserOperationResult()
Przekroczony limit użytkownika
to typowe przyczyny niepowodzenia:
Utworzenie użytkownika może trochę potrwać. Jeśli często tworzysz konta użytkowników, możesz poprawić wrażenia użytkowników, przygotowując gotowych do użycia je w tle; Konieczne może być zachowanie równowagi między zaletami gotowego użytkownika a maksymalnym dozwolonej liczby użytkowników na urządzeniu.
Identyfikacja
Po utworzeniu nowego użytkownika należy odwołać się do niego za pomocą stałego numeru seryjnego
numer. Nie zachowuj tych elementów (UserHandle
), ponieważ system wykorzystuje je ponownie
tworzyć i usuwać konta użytkowników. Zadzwoń, aby uzyskać numer seryjny
UserManager.getSerialNumberForUser()
:
Kotlin
// After calling createAndManageUser() use a device-unique serial number // (that isn’t recycled) to identify the new user. secondaryUser?.let { val userManager = getContext().getSystemService(UserManager::class.java) val ephemeralUserId = userManager!!.getSerialNumberForUser(it) // Save the serial number to storage ... }
Java
// After calling createAndManageUser() use a device-unique serial number // (that isn’t recycled) to identify the new user. if (secondaryUser != null) { UserManager userManager = getContext().getSystemService(UserManager.class); long ephemeralUserId = userManager.getSerialNumberForUser(secondaryUser); // Save the serial number to storage ... }
Konfiguracja użytkownika
W zależności od potrzeb użytkowników możesz dostosować konfigurację dodatkowych
użytkowników. Podczas wywoływania funkcji createAndManageUser()
możesz uwzględnić te flagi:
SKIP_SETUP_WIZARD
- Pomija korzystanie z kreatora konfiguracji dla nowego użytkownika, który sprawdza dostępność aktualizacji i je instaluje. prosi użytkownika o dodanie konta Google wraz z usługami Google, a następnie ustawia blokady ekranu. Może to zająć trochę czasu i może nie mieć zastosowania w niektórych przypadkach dla użytkowników, takich jak publiczne kioski internetowe.
LEAVE_ALL_SYSTEM_APPS_ENABLED
- Wszystkie aplikacje systemowe będą włączone na koncie nowego użytkownika. Jeśli nie ustawisz tej flagi, Zawiera on jedynie minimalny zestaw aplikacji potrzebnych telefonowi zwykle jest to przeglądarka plików, aplikacja do wybierania numerów, kontakty i wiadomości SMS.
Przestrzegaj cyklu życia użytkownika
DPC (jeśli jest administratorem w pełni zarządzanego urządzenia) może przydać się do:
możesz otrzymywać powiadomienia o zmianach użytkowników pomocniczych. Aby uruchamiać zadania dodatkowe po wprowadzeniu zmian, zastąp zastąpienie
te metody wywołania zwrotnego w podklasie DeviceAdminReceiver
DPC:
onUserStarted()
- Wywoływane po uruchomieniu systemu przez użytkownika. Ten użytkownik może nadal konfigurować urządzenie lub
działać w tle. Użytkownika możesz uzyskać w
startedUser
. onUserSwitched()
- Wywoływane po przełączeniu systemu na innego użytkownika. Nowego użytkownika możesz
która działa na pierwszym planie z argumentu
switchedUser
. onUserStopped()
- Wywoływane po zatrzymaniu użytkownika przez system, ponieważ użytkownik się wylogował, a następnie przełączył się na
nowego użytkownika (jeśli użytkownik jest tymczasowy) lub system DPC go zatrzymał. Możesz uzyskać
użytkownika z argumentu
stoppedUser
. onUserAdded()
- Wywoływana, gdy system dodaje nowego użytkownika. Zazwyczaj użytkownicy dodatkowi nie
skonfigurować pełną konfigurację, kiedy DPC otrzyma wywołanie zwrotne. Aby uzyskać informacje o użytkowniku,
newUser
argument. onUserRemoved()
- Wywoływana po usunięciu użytkownika przez system. Ponieważ konto użytkownika zostało już usunięte,
nie możesz uzyskać dostępu do użytkownika reprezentowanego przez argument
removedUser
.
Aby wiedzieć, kiedy system przenosi użytkownika na pierwszy plan lub wysyła go na
w tle, aplikacje mogą rejestrować odbiornik
ACTION_USER_FOREGROUND
i
ACTION_USER_BACKGROUND
transmisji.
Odkryj użytkowników
Aby pobrać wszystkich użytkowników pomocniczych, administrator w pełni zarządzanego urządzenia może zadzwonić do:
DevicePolicyManager.getSecondaryUsers()
Wyniki
uwzględniania wszystkich użytkowników dodatkowych lub tymczasowych, utworzonych przez administratora. Dodatkowo wyniki wyszukiwania
użytkowników dodatkowych (lub gościa), którzy mogą korzystać z urządzenia
utworzone przez użytkowników. Wyniki nie obejmują profili służbowych, ponieważ nie są
i innymi użytkownikami. Z przykładu poniżej dowiesz się, jak możesz używać tej metody:
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); }
Oto inne metody, które można wywołać, aby sprawdzić stan użytkowników dodatkowych:
DevicePolicyManager.isEphemeralUser()
- Wywołaj tę metodę administratora użytkownika dodatkowego, aby sprawdzić, czy jest to użytkownik tymczasowy.
DevicePolicyManager.isAffiliatedUser()
- Wywołaj tę metodę administratora konta użytkownika dodatkowego, aby sprawdzić, czy ten użytkownik powiązane z głównym użytkownikiem. Więcej informacji o powiązaniu znajdziesz na stronie DPC poniżej.
Zarządzanie użytkownikami
Jeśli chcesz w pełni zarządzać cyklem życia użytkownika, możesz wywołać interfejsy API: szczegółowa kontrola nad tym, kiedy i w jaki sposób urządzenie zmienia użytkowników. Na przykład: możesz usunąć konto użytkownika, jeśli urządzenie nie było używane od jakiegoś czasu lub możesz wysyłania niewysłanych zamówień na serwer przed zakończeniem pracy użytkownika.
Wyloguj
W Androidzie 9.0 dodaliśmy przycisk wylogowania do ekranu blokady, dzięki czemu osoba korzystająca z może zakończyć sesję. Po dotknięciu przycisku system zatrzymuje użytkownik dodatkowy, usuwa konto użytkownika, jeśli jest ono efemeryczne, a użytkownik główny powraca na pierwszy plan. Android ukrywa przycisk, gdy główny użytkownik znajduje się na ponieważ główny użytkownik nie może się wylogować.
Domyślnie Android nie wyświetla przycisku zakończenia sesji, ale administrator (
w pełni zarządzanym urządzeniu) mogą je włączyć, łącząc się
DevicePolicyManager.setLogoutEnabled()
W razie potrzeby
potwierdź obecny stan przycisku, wywołaj
DevicePolicyManager.isLogoutEnabled()
Administrator użytkownika dodatkowego może automatycznie wylogować użytkownika i wrócić do niego
głównemu użytkownikowi. Najpierw sprawdź, czy główni i dodatkowi użytkownicy są
stowarzyszony, a następnie zadzwoń pod numer DevicePolicyManager.logoutUser()
. Jeśli
wylogowany użytkownik jest użytkownikiem tymczasowym, system zatrzymuje się, a następnie usuwa
użytkownika.
Przełącz użytkownika
Aby przełączyć się na innego użytkownika dodatkowego, administrator w pełni zarządzanego urządzenia może
zadzwoń do: DevicePolicyManager.switchUser()
. Dla wygody
może przekazać użytkownikowi null
, aby został głównym użytkownikiem.
Zatrzymywanie użytkownika
Aby zatrzymać użytkownika dodatkowego, DPC, które jest właścicielem w pełni zarządzanego urządzenia, może zadzwonić
DevicePolicyManager.stopUser()
Jeśli zatrzymany użytkownik to
użytkownik zostaje zatrzymany, a następnie usunięty.
O ile to możliwe, zalecamy zatrzymanie użytkowników, aby uniknąć ograniczenia działania urządzenia z maksymalną liczbą aktywnych użytkowników.
Usuwanie użytkownika
Aby trwale usunąć użytkownika dodatkowego, DPC może wywołać jedną z tych czynności:
DevicePolicyManager
metody:
- Administrator w pełni zarządzanego urządzenia może zadzwonić pod numer
removeUser()
. - Administrator użytkownika dodatkowego może wywołać metodę
wipeData()
.
System usuwa użytkowników tymczasowych, gdy są zalogowani, zatrzymani lub przełączeni z daleka.
Wyłącz domyślny interfejs użytkownika
Jeśli DPC udostępnia interfejs do zarządzania użytkownikami, możesz wyłączyć wbudowane aplikacje na Androida
do wykorzystania przez wielu użytkowników. Aby to zrobić, zadzwoń pod numer
DevicePolicyManager.setLogoutEnabled()
i dodanie funkcji
Ograniczenie DISALLOW_USER_SWITCH
wyświetlane w
następujący przykład:
Kotlin
// Explicitly disallow logging out using Android UI (disabled by default). dpm.setLogoutEnabled(adminName, false) // Disallow switching users in Android's UI. This DPC can still // call switchUser() to manage users. dpm.addUserRestriction(adminName, UserManager.DISALLOW_USER_SWITCH)
Java
// Explicitly disallow logging out using Android UI (disabled by default). dpm.setLogoutEnabled(adminName, false); // Disallow switching users in Android's UI. This DPC can still // call switchUser() to manage users. dpm.addUserRestriction(adminName, UserManager.DISALLOW_USER_SWITCH);
Osoba używająca urządzenia nie może dodawać użytkowników pomocniczych, używając wbudowanego interfejsu Androida.
bo administratorzy w pełni zarządzanych urządzeń automatycznie dodają
Ograniczenie dotyczące użytkownika DISALLOW_ADD_USER
.
Komunikaty dotyczące sesji
Gdy osoba używająca urządzenia przełącza się na nowego użytkownika, Android pokazuje panel, zaznacz przełącznik. Android wyświetla te komunikaty:
- Komunikat rozpoczynania sesji użytkownika wyświetlany, gdy urządzenie przełącza się na pomocniczą głównego użytkownika.
- Komunikat dotyczący sesji użytkownika wyświetlany, gdy urządzenie wraca do głównego użytkownika przez użytkownika dodatkowego.
System nie wyświetla komunikatów podczas przełączania się między 2 użytkownikami pomocniczymi.
Wiadomości mogą nie być odpowiednie we wszystkich sytuacjach, więc możesz zmienić treść tych wiadomości. Jeśli na przykład rozwiązanie używa tymczasowego użytkownika sesji, może to być odzwierciedlone w komunikatach takich jak: Zatrzymywanie przeglądarki sesja i usuwam dane osobowe...
System wyświetla wiadomość przez kilka sekund, więc każda wiadomość
powinna być krótka, jasna. Aby dostosować wiadomości, administrator może zadzwonić
metody DevicePolicyManager
setStartUserSessionMessage()
i
setEndUserSessionMessage()
zgodnie z
następujący przykład:
Kotlin
// Short, 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, easy-to-read messages shown at the start and end of a session. // In your app, store these strings in a localizable resource. private static final String START_USER_SESSION_MESSAGE = "Starting guest session…"; private static final String END_USER_SESSION_MESSAGE = "Stopping & clearing data…"; // ... dpm.setStartUserSessionMessage(adminName, START_USER_SESSION_MESSAGE); dpm.setEndUserSessionMessage(adminName, END_USER_SESSION_MESSAGE);
Przekaż null
, aby usunąć swoje wiadomości i wrócić do ustawień domyślnych Androida
wiadomości. Jeśli chcesz sprawdzić bieżący tekst wiadomości, zadzwoń pod
getStartUserSessionMessage()
lub
getEndUserSessionMessage()
DPC powinien ustawić zlokalizowane komunikaty dla bieżącego języka użytkownika. Musisz również zaktualizować wiadomości, gdy zmiany języka użytkownika:
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.string.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:name="android.intent.action.LOCALE_CHANGED" /> // intent filter for our DeviceAdminReceiver subclass in the app manifest file. if (intent.getAction().equals(ACTION_LOCALE_CHANGED)) { // Android's resources return 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); }
Koordynacja DPC
Zarządzanie użytkownikami pomocniczymi zwykle wymaga 2 instancji DPC – jednej z na w pełni zarządzanym urządzeniu, a drugie jest właścicielem użytkownika dodatkowego. Podczas tworzenia nowego użytkownika, administrator w pełni zarządzanego urządzenia ustawi kolejną instancję jako administratora nowego użytkownika.
powiązani użytkownicy
Niektóre interfejsy API wymienione w tym przewodniku dla programistów działają tylko wtedy, gdy użytkownicy dodatkowi są stowarzyszone. Android wyłącza niektóre funkcje (na przykład logowania sieciowego) podczas dodawania nowych niepowiązanych użytkowników dodatkowych do urządzenia, należy jak najszybciej powiązać użytkowników. Zobacz przykład tutaj: Konfiguracja poniżej.
Konfiguracja
Skonfiguruj nowych użytkowników dodatkowych (z DPC, do którego należy konto użytkownika dodatkowego) przed
i umożliwiać ludziom korzystanie z nich. Możesz to zrobić na stronie
DeviceAdminReceiver.onEnabled()
– wywołanie zwrotne. Jeśli wcześniej
ustaw wszelkie dodatki administracyjne podczas rozmowy na createAndManageUser()
, możesz uzyskać
wartości z argumentu intent
. Oto przykład powiązania z DPC
nowego użytkownika dodatkowego w wywołaniu zwrotnym:
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(it)) } // 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 != null) { DevicePolicyManager dpm = getManager(context); dpm.setAffiliationIds(getWho(context), new HashSet<String>(Arrays.asList(affiliationId))); } // Continue setup of the new secondary user ... }
RPC między kontrolerami DPC
Mimo że 2 instancje DPC są uruchomione w ramach osobnych użytkowników,
do użytkowników urządzenia, a użytkownicy dodatkowi mogą się ze sobą komunikować.
Wywołanie innej usługi DPC przekracza granice użytkowników, więc Twój DPC nie może
Wywołaj bindService()
w taki sam sposób, jakby
na urządzeniach z Androidem. Aby utworzyć powiązanie z usługą działającą w
inny użytkownik, wywołaj
DevicePolicyManager.bindDeviceAdminServiceAsUser()
DPC może tworzyć powiązania tylko z usługami uruchomionymi dla użytkowników zwróconych przez
DevicePolicyManager.getBindDeviceAdminTargetUsers()
Poniższy przykład pokazuje administratora dodatkowego powiązania użytkownika z administratorem
w pełni zarządzanego urządzenia:
Kotlin
// From a secondary user, the list contains just the primary user. dpm.getBindDeviceAdminTargetUsers(adminName).forEach { // Set up the callbacks for the service connection. val intent = Intent(mContext, FullyManagedDeviceService::class.java) val serviceconnection = object : ServiceConnection { override fun onServiceConnected(componentName: ComponentName, iBinder: IBinder) { // Call methods on service ... } override fun onServiceDisconnected(componentName: ComponentName) { // Clean up or reconnect if needed ... } } // Bind to the service as the primary user [it]. val bindSuccessful = dpm.bindDeviceAdminServiceAsUser(adminName, intent, serviceconnection, Context.BIND_AUTO_CREATE, it) }
Java
// From a secondary user, the list contains just the primary user. List<UserHandle> targetUsers = dpm.getBindDeviceAdminTargetUsers(adminName); if (targetUsers.isEmpty()) { // If the users aren't affiliated, the list doesn't contain any users. return; } // Set up the callbacks for the service connection. Intent intent = new Intent(mContext, FullyManagedDeviceService.class); 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 ... } }; // Bind to the service as the primary user. UserHandle primaryUser = targetUsers.get(0); boolean bindSuccessful = dpm.bindDeviceAdminServiceAsUser( adminName, intent, serviceconnection, Context.BIND_AUTO_CREATE, primaryUser);
Dodatkowe materiały
Więcej informacji o urządzeniach specjalnych znajdziesz w tych dokumentach:
- Omówienie urządzeń specjalnych zawiera omówienie: urządzeń specjalnych.
- Blokowanie trybu zadań wyjaśnia, jak: blokować na danym urządzeniu pojedynczą aplikację lub zestaw aplikacji.
- Książka kucharska na specjalnych urządzeniach – kolejne przykłady, które pozwalają ograniczyć użycie urządzeń specjalnych i ulepszyć działanie usługi. i uzyskiwanie dodatkowych informacji.