Le funzionalità riportate in questa guida descrivono le funzionalità di gestione della sicurezza che puoi implementare nella tua app controller dei criteri dei dispositivi (DPC). Questo documento contiene esempi di codice; inoltre, puoi utilizzare l'app DPC di test come fonte di codice campione per le funzionalità aziendali di Android.
Un'app DPC può essere eseguita in modalità proprietario del profilo sui dispositivi personali o in modalità proprietario del dispositivo sui dispositivi completamente gestiti. Questa tabella indica le funzionalità disponibili quando il DPC viene eseguito in modalità proprietario profilo o proprietario del dispositivo:
Funzionalità | Proprietario del profilo | Proprietario del dispositivo |
---|---|---|
Disattivare l'accesso alle app | ✓ | ✓ |
Bloccare app da origini sconosciute | ✓ | ✓ |
Limitare gli account in Google Play | ✓ | ✓ |
Attivare la protezione dal ripristino dei dati di fabbrica aziendale | ✓ | |
Monitorare i log dei processi aziendali e le segnalazioni di bug da remoto | ✓ | |
Concedere l'accesso a un certificato client e rimuoverlo | ✓ | ✓ |
Reimpostazione sicura del passcode | ✓ | ✓ |
Verifica della sicurezza del profilo di lavoro | ✓ |
Disattivare l'accesso alle app
Per le organizzazioni che vogliono impedire ai dipendenti di giocare o guardare YouTube sul proprio dispositivo Android in determinate ore del giorno o in determinati giorni della settimana, un DPC può disattivare temporaneamente l'accesso alle app.
Per disattivare l'accesso alle app, un DPC in esecuzione in modalità proprietario del dispositivo o proprietario del profilo configura setPackagesSuspended()
, dopodiché l'app selezionata si comporta come se fosse disattivata (l'Avvio app di Google rende l'app non selezionabile). Quando un utente tocca un'app, vede una finestra
di sistema che indica che l'app è sospesa.
Mentre un'app è sospesa, non può avviare le attività e le notifiche al pacchetto vengono soppresse. I pacchi sospesi non vengono visualizzati nella schermata Panoramica, non possono mostrare finestre di dialogo (inclusi toast e snackbar) e non possono riprodurre l'audio o vibrare il dispositivo.
Avvio app può sapere se un'app è sospesa chiamando il metodo isPackageSuspended()
. Per maggiori dettagli su come configurare la sospensione delle app, consulta setPackagesSuspended
.
Blocca app da origini sconosciute
Le app che non vengono installate da Google Play (o da altri store attendibili) sono chiamate app di origini sconosciute. I dispositivi e i dati possono essere più a rischio quando gli utenti installano queste app.
Per impedire a un utente di installare app da origini sconosciute, i componenti di amministrazione dei dispositivi completamente gestiti e dei profili di lavoro possono aggiungere la limitazione utente di DISALLOW_INSTALL_UNKNOWN_SOURCES
.
Limitazione a livello di dispositivo del profilo di lavoro
Quando l'amministratore di un profilo di lavoro aggiunge DISALLOW_INSTALL_UNKNOWN_SOURCES
, la limitazione si applica solo al profilo di lavoro. Tuttavia, l'amministratore di un profilo di lavoro può applicare una limitazione a livello di dispositivo impostando una configurazione gestita per Google Play. La limitazione a livello di dispositivo è disponibile in Android 8.0 (o versioni successive) se l'app Google Play installata è la versione 80812500 o successive.
Per limitare le installazioni di app a Google Play, procedi nel seguente modo:
- Imposta un bundle di configurazione gestito per il pacchetto Google Play
com.android.vending
. - Nel bundle, inserisci un valore booleano per la chiave
verify_apps:device_wide_unknown_source_block
. - Aggiungi la restrizione relativa agli utenti per
ENSURE_VERIFY_APPS
.
L'esempio seguente mostra come verificare che Google Play supporti questa impostazione e impostare il valore su true
:
Kotlin
internal val DEVICE_WIDE_UNKNOWN_SOURCES = "verify_apps:device_wide_unknown_source_block" internal val GOOGLE_PLAY_APK = "com.android.vending" // ... // Add the setting to Google Play's existing managed config. Supported in // Google Play version 80812500 or higher--older versions ignore unsupported // settings. val dpm = context.getSystemService(Context.DEVICE_POLICY_SERVICE) as DevicePolicyManager var existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK) val newConfig = Bundle(existingConfig) newConfig.putBoolean(DEVICE_WIDE_UNKNOWN_SOURCES, true) dpm.setApplicationRestrictions(adminName, GOOGLE_PLAY_APK, newConfig) // Make sure that Google Play Protect verifies apps. dpm.addUserRestriction(adminName, UserManager.ENSURE_VERIFY_APPS) dpm.addUserRestriction(adminName, UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES)
Java
static final String DEVICE_WIDE_UNKNOWN_SOURCES = "verify_apps:device_wide_unknown_source_block"; static final String GOOGLE_PLAY_APK = "com.android.vending"; // ... // Add the setting to Google Play's existing managed config. Supported in // Google Play version 80812500 or higher--older versions ignore unsupported // settings. DevicePolicyManager dpm = (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE); Bundle existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK); Bundle newConfig = new Bundle(existingConfig); newConfig.putBoolean(DEVICE_WIDE_UNKNOWN_SOURCES, true); dpm.setApplicationRestrictions(adminName, GOOGLE_PLAY_APK, newConfig); // Make sure that Google Play Protect verifies apps. dpm.addUserRestriction(adminName, UserManager.ENSURE_VERIFY_APPS); dpm.addUserRestriction(adminName, UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES);
L'interfaccia utente nelle impostazioni di sistema rimane attiva, ma il sistema blocca l'installazione delle app. Questa limitazione influisce sulle installazioni future: le app installate in precedenza rimangono sul dispositivo. Gli utenti dei dispositivi possono continuare a installare app nel profilo personale utilizzando Android Debug Bridge (adb).
Per scoprire di più sulle origini sconosciute, consulta Opzioni di distribuzione alternativa.
Limitare gli account in Google Play
A volte un'organizzazione potrebbe voler consentire alle persone di aggiungere Account Google personali (ad esempio per leggere la posta in Gmail), ma non vuole che l'account personale installi app. Il DPC può impostare un elenco di account che gli utenti possono utilizzare in Google Play.
I componenti di amministrazione dei dispositivi completamente gestiti o dei profili di lavoro possono limitare gli account impostando una configurazione gestita per Google Play. La limitazione dell'account è disponibile se la versione dell'app Google Play installata è 80970100 o successive.
Per limitare gli account in Google Play:
- Imposta un bundle di configurazione gestito per il pacchetto Google Play
com.android.vending
. - Nel bundle, inserisci gli indirizzi email separati da virgole come valore stringa per la chiave
allowed_accounts
.
L'esempio seguente mostra come limitare gli account:
Kotlin
internal val ALLOWED_ACCOUNTS = "allowed_accounts" internal val GOOGLE_PLAY_APK = "com.android.vending" // ... // Limit Google Play to one work and one personal account. Use // a comma-separated list of account email addresses (usernames). val googleAccounts = "ali@gmail.com,ali.connors@example.com" // Supported in Google Play version 80970100 or higher. val existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK) val newConfig = Bundle(existingConfig) newConfig.putString(ALLOWED_ACCOUNTS, googleAccounts) dpm.setApplicationRestrictions(adminName, GOOGLE_PLAY_APK, newConfig)
Java
static final String ALLOWED_ACCOUNTS = "allowed_accounts"; static final String GOOGLE_PLAY_APK = "com.android.vending"; // ... // Limit Google Play to one work and one personal account. Use // a comma-separated list of account email addresses (usernames). String googleAccounts = "ali@gmail.com,ali.connors@example.com"; // Supported in Google Play version 80970100 or higher. Bundle existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK); Bundle newConfig = new Bundle(existingConfig); newConfig.putString(ALLOWED_ACCOUNTS, googleAccounts); dpm.setApplicationRestrictions(adminName, GOOGLE_PLAY_APK, newConfig);
Per limitare Google Play solo all'account di lavoro, imposta allowed_accounts
sull'unico account gestito non appena il DPC conosce l'indirizzo email dell'account. Una stringa vuota impedisce agli utenti di utilizzare qualsiasi account in Google Play.
Attivare la protezione di ripristino dei dati di fabbrica aziendale
Utilizzando la protezione aziendale dal ripristino dei dati di fabbrica, le organizzazioni possono specificare quali Account Google possono eseguire il provisioning di un dispositivo di cui è stato eseguito il ripristino dei dati di fabbrica.
La protezione di ripristino dei dati di fabbrica per i consumatori è progettata per scoraggiare il furto del dispositivo. Prima di consentire a chiunque di eseguire il provisioning del dispositivo dopo un ripristino dei dati di fabbrica non autorizzato (ad esempio tramite un EMM), la configurazione guidata richiede all'utente di eseguire l'autenticazione utilizzando qualsiasi Account Google precedentemente presente sul profilo personale del dispositivo.
In un ambiente aziendale, il ripristino dei dati di fabbrica è uno strumento importante per la gestione dei dispositivi dei dipendenti quando lasciano l'organizzazione. Tuttavia, se l'organizzazione non conosce le credenziali dell'account di un dipendente, la protezione del ripristino dei dati di fabbrica può impedire all'organizzazione di fornire un dispositivo a un altro dipendente.
Controllare il provisioning dopo un ripristino dei dati di fabbrica
Quando viene eseguito in modalità proprietario del dispositivo, il DPC può utilizzare setFactoryResetProtectionPolicy()
per controllare quali account sono autorizzati a eseguire il provisioning di un dispositivo dopo un ripristino dei dati di fabbrica. Se questa configurazione è impostata su null
o su un elenco vuoto, gli account autorizzati a eseguire il provisioning di un dispositivo dopo un ripristino dei dati di fabbrica sono gli account sul profilo personale del dispositivo.
Un DPC può configurare questi account per l'intera durata di un dispositivo completamente gestito.
- L'amministratore IT può utilizzare il metodo
people.get
dell'API People con il valore specialeme
. Viene recuperato iluserId
per l'account a cui è stato eseguito l'accesso.userID
viene restituito nella chiaveresourceName
nel formatopeople/[userId]
sotto forma di stringa intera. I nuovi account creati potrebbero non essere disponibili per il ripristino dei dati di fabbrica per 72 ore. - Potresti anche voler consentire a uno o più amministratori IT di sbloccare il dispositivo dopo un ripristino dei dati di fabbrica. Chiedi a ciascuno di questi amministratori IT di accedere al proprio Account Google e di seguire anche il passaggio 1 e di condividere i propri
userId
con te, così potrai aggiungere questiuserIds
all'elenco nel passaggio successivo. - Il DPC imposta una limitazione appropriata delle app utilizzando
setFactoryResetProtectionPolicy()
per impostare l'elenco diuserId
che può eseguire il provisioning di un dispositivo di cui è stato eseguito il ripristino dei dati di fabbrica. - Il DPC abilita gli account che possono eseguire il provisioning dei dispositivi dopo il ripristino dei dati di fabbrica inviando la trasmissione
com.google.android.gms.auth.FRP_CONFIG_CHANGED
come intento esplicito per evitare che venga persa a causa di restrizioni in background.
Kotlin
const val ACTION_FRP_CONFIG_CHANGED = "com.google.android.gms.auth.FRP_CONFIG_CHANGED" const val GMSCORE_PACKAGE = "com.google.android.gms" // ... // List of userId that can provision a factory reset device. // You can use the value returned calling people/me endpoint. val accountIds = listOf("000000000000000000000") dpm.setFactoryResetProtectionPolicy( adminName, FactoryResetProtectionPolicy.Builder() .setFactoryResetProtectionAccounts(accountIds) .setFactoryResetProtectionEnabled(true) .build() ) val frpChangedIntent = Intent(ACTION_FRP_CONFIG_CHANGED) frpChangedIntent.setPackage(GMSCORE_PACKAGE) context.sendBroadcast(frpChangedIntent)
Java
static final String ACTION_FRP_CONFIG_CHANGED = "com.google.android.gms.auth.FRP_CONFIG_CHANGED"; static final String GMSCORE_PACKAGE = "com.google.android.gms"; // ... // List of userId that can provision a factory reset device. // You can use the value returned calling people/me endpoint. List<String> accountIds = new ArrayList<String>(); accountIds.add("000000000000000000000"); dpm.setFactoryResetProtectionPolicy( adminName, new FactoryResetProtectionPolicy.Builder() .setFactoryResetProtectionAccounts(accountIds) .setFactoryResetProtectionEnabled(true) .build()); Intent frpChangedIntent = new Intent(ACTION_FRP_CONFIG_CHANGED); frpChangedIntent.setPackage(GMSCORE_PACKAGE); context.sendBroadcast(frpChangedIntent);
Legacy
Per i dispositivi che non possono utilizzare setFactoryResetProtectionPolicy()
, introdotto con il Livello API 30, il DPC può utilizzare setApplicationRestrictions
per aggiungere gli account scelti alla configurazione gestita factoryResetProtectionAdmin
per il pacchetto com.google.android.gms
.
Kotlin
const val GOOGLE_PLAY_APK = "com.android.vending" const val FACTORY_RESET_PROTECTION_ADMIN = "factoryResetProtectionAdmin" const val DISABLE_FACTORY_RESET_PROTECTION_ADMIN = "disableFactoryResetProtectionAdmin" const val GMSCORE_PACKAGE = "com.google.android.gms" // ... val existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK) val newConfig = Bundle(existingConfig) newConfig.putBoolean(DISABLE_FACTORY_RESET_PROTECTION_ADMIN, false) newConfig.putString(FACTORY_RESET_PROTECTION_ADMIN, googleAccounts) dpm.setApplicationRestrictions(adminName, GOOGLE_PLAY_APK, newConfig) val frpChangedIntent = Intent(ACTION_FRP_CONFIG_CHANGED) frpChangedIntent.setPackage(GMSCORE_PACKAGE) context.sendBroadcast(frpChangedIntent)
Java
static final String GOOGLE_PLAY_APK = "com.android.vending"; static final String FACTORY_RESET_PROTECTION_ADMIN = "factoryResetProtectionAdmin"; static final String DISABLE_FACTORY_RESET_PROTECTION_ADMIN = "disableFactoryResetProtectionAdmin"; static final String GMSCORE_PACKAGE = "com.google.android.gms"; // ... Bundle existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK); Bundle newConfig = new Bundle(existingConfig); newConfig.putBoolean(DISABLE_FACTORY_RESET_PROTECTION_ADMIN, false); newConfig.putStringArray(FACTORY_RESET_PROTECTION_ADMIN, accountIds.toArray(new String[accountIds.size()])); dpm.setApplicationRestrictions(adminName, GOOGLE_PLAY_APK, newConfig); Intent frpChangedIntent = new Intent(ACTION_FRP_CONFIG_CHANGED); frpChangedIntent.setPackage(GMSCORE_PACKAGE); context.sendBroadcast(frpChangedIntent);
Disattivare la protezione ripristino dati di fabbrica aziendale
Per disattivare la protezione dal ripristino dei dati di fabbrica, il DPC può utilizzare
setFactoryResetProtectionPolicy()
il superamento del valore null
.
Kotlin
const val ACTION_FRP_CONFIG_CHANGED = "com.google.android.gms.auth.FRP_CONFIG_CHANGED" const val GMSCORE_PACKAGE = "com.google.android.gms" // ... dpm.setFactoryResetProtectionPolicy(adminName, null) val frpChangedIntent = Intent(ACTION_FRP_CONFIG_CHANGED) frpChangedIntent.setPackage(GMSCORE_PACKAGE) context.sendBroadcast(frpChangedIntent)
Java
static final String ACTION_FRP_CONFIG_CHANGED = "com.google.android.gms.auth.FRP_CONFIG_CHANGED"; static final String GMSCORE_PACKAGE = "com.google.android.gms"; // ... dpm.setFactoryResetProtectionPolicy(adminName, null); Intent frpChangedIntent = new Intent(ACTION_FRP_CONFIG_CHANGED); frpChangedIntent.setPackage(GMSCORE_PACKAGE); context.sendBroadcast(frpChangedIntent);
Legacy
Per i dispositivi che non possono utilizzare setFactoryResetProtectionPolicy()
, introdotto con il Livello API 30, il DPC può utilizzare setApplicationRestrictions
per impostare una coppia chiave-valore true
nella configurazione gestita di disableFactoryResetProtectionAdmin
per il pacchetto com.google.android.gms
.
Kotlin
const val GOOGLE_PLAY_APK = "com.android.vending" const val FACTORY_RESET_PROTECTION_ADMIN = "factoryResetProtectionAdmin" const val DISABLE_FACTORY_RESET_PROTECTION_ADMIN = "disableFactoryResetProtectionAdmin" const val GMSCORE_PACKAGE = "com.google.android.gms" // ... val existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK) val newConfig = Bundle(existingConfig) newConfig.putBoolean(DISABLE_FACTORY_RESET_PROTECTION_ADMIN, true) dpm.setApplicationRestrictions( adminName, GOOGLE_PLAY_SERVICES_PACKAGE, restrictions ) val frpChangedIntent = Intent(ACTION_FRP_CONFIG_CHANGED) frpChangedIntent.setPackage(GMSCORE_PACKAGE) context.sendBroadcast(frpChangedIntent)
Java
static final String GOOGLE_PLAY_APK = "com.android.vending"; static final String FACTORY_RESET_PROTECTION_ADMIN = "factoryResetProtectionAdmin"; static final String DISABLE_FACTORY_RESET_PROTECTION_ADMIN = "disableFactoryResetProtectionAdmin"; static final String GMSCORE_PACKAGE = "com.google.android.gms"; // ... Bundle existingConfig = dpm.getApplicationRestrictions(adminName, GOOGLE_PLAY_APK); Bundle newConfig = new Bundle(existingConfig); newConfig.putBoolean(DISABLE_FACTORY_RESET_PROTECTION_ADMIN, true); dpm.setApplicationRestrictions( adminName, GOOGLE_PLAY_SERVICES_PACKAGE, restrictions); Intent frpChangedIntent = new Intent(ACTION_FRP_CONFIG_CHANGED); frpChangedIntent.setPackage(GMSCORE_PACKAGE); context.sendBroadcast(frpChangedIntent);
Monitora i log dei processi aziendali e le segnalazioni di bug da remoto
Nella console EMM, un amministratore può monitorare i dispositivi completamente gestiti utilizzando i log dei processi aziendali e le segnalazioni di bug da remoto.
Registra attività del dispositivo aziendale
Un DPC in esecuzione in modalità proprietario del dispositivo può identificare le attività sospette monitorando da remoto l'attività del dispositivo, inclusi i lanci di app, l'attività di Android Debug Bridge (adb) e gli sblocchi dello schermo. I log dei processi non richiedono il consenso dell'utente.
Per attivare o disattivare il logging, un DPC chiama setSecurityLoggingEnabled()
.
Quando è disponibile un nuovo batch di log, un DeviceAdminReceiver
riceve il callback
onSecurityLogsAvailable()
. Per recuperare i log (dopo aver ricevuto il callback), un DPC chiama retrieveSecurityLogs()
.
I DPC possono anche chiamare retrievePreRebootSecurityLogs()
per recuperare i log di sicurezza generati nel ciclo di riavvio precedente. Questo è l'intervallo tra l'ultimo riavvio del dispositivo e quello precedente. I dispositivi che non supportano retrieveSecurityLogs()
restituiscono null
. Se la tua app recupera i log utilizzando sia retrievePreRebootSecurityLogs()
sia retrieveSecurityLogs()
, devi verificare la presenza di voci duplicate.
Nota: questa funzionalità registra solo le attività su dispositivi completamente gestiti su cui sono presenti un singolo utente o utenti affiliati. Questa funzionalità non funziona sui dispositivi personali, perché registra l'attività a livello di dispositivo.
Questa impostazione può essere utile nel controllo post-evento di sicurezza perché registra i seguenti tipi di azioni:
- Ogni volta che l'app è stata avviata di recente. Questo potrebbe essere utile per identificare se è presente malware che inizia con un'app compromessa.
- Tentativi di sblocco non riusciti su un dispositivo. Ciò potrebbe identificare se sono presenti diversi tentativi di sblocco non riusciti in un breve periodo di tempo.
- Comandi adb potenzialmente dannosi quando un utente collega il dispositivo a un computer con un cavo USB.
Per maggiori dettagli su come leggere i log, vedi SecurityLog
.
Durante la fase di sviluppo e test, puoi forzare il sistema a rendere disponibili i log di sicurezza esistenti al tuo DPC, senza dover attendere un batch completo. In Android 9.0 (livello API 28) o versioni successive, esegui il seguente comando Android Debug Bridge (adb) nel terminale:
adb shell dpm force-security-logs
Il sistema limita la frequenza con cui puoi utilizzare lo strumento e segnala eventuali rallentamenti involontari nell'output del terminale. Se sono disponibili log, il DPC riceve il callback onSecurityLogsAvailable()
.
Richiedere una segnalazione di bug da remoto
Un DPC eseguito in modalità proprietario del dispositivo può richiedere da remoto segnalazioni di bug per i dispositivi degli utenti con un solo utente o utenti affiliati. La segnalazione di bug acquisisce l'attività del dispositivo nell'esatto momento in cui viene richiesta la segnalazione di bug, ma potrebbe anche includere l'attività delle ore precedenti, a seconda della frequenza di aggiornamento del buffer logcat.
Per richiedere da remoto le segnalazioni di bug, il DPC chiama requestBugreport()
:
- Se un utente accetta di condividere la segnalazione di bug, il DPC riceve la segnalazione utilizzando
onBugreportShared()
. - Se un utente nega la condivisione della segnalazione di bug, il DPC riceve un messaggio di richiesta di condivisione negata utilizzando
onBugreportSharingDeclined()
. - Se la segnalazione di bug non va a buon fine, il DPC vede
onBugreportFailed()
conBUGREPORT_FAILURE_FAILED_COMPLETING
oBUGREPORT_FAILURE_FILE_NO_LONGER_AVAILABLE
.
Concedere l'accesso a un certificato client e rimuoverlo
Se un DPC in esecuzione in modalità proprietario del profilo o proprietario del dispositivo concede a un'app di terze parti la possibilità di gestire i certificati, l'app può concedersi l'accesso ai certificati che installa senza l'intervento di un utente. Per installare un
certificato a cui possono accedere tutte le app di un profilo, utilizza installKeyPair()
.
Per i parametri da configurare, consulta installKeyPair()
. Questa funzionalità funziona in combinazione con l'API esistente per la gestione dei certificati.
Scenario di deployment
Senza il metodo installKeyPair()
:
- Gli utenti devono toccare il nome del certificato e Consenti ogni volta che vogliono concedere l'accesso a un certificato.
- Quando installano un certificato, gli utenti visualizzano un messaggio che richiede di assegnare un nome.
Con il metodo installKeyPair()
:
- Gli utenti non devono toccare Consenti ogni volta che vogliono concedere l'accesso a un certificato.
- Gli utenti non possono rinominare i certificati.
- Gli amministratori hanno maggiore controllo in quanto possono bloccare i certificati per le app che non dovrebbero avere accesso a certificati specifici.
Rimuovere un certificato client
Dopo aver concesso l'accesso a un certificato client, per rimuovere da remoto i certificati client installati tramite installKeyPair()
, chiama removeKeyPair()
.
Un DPC in esecuzione in modalità proprietario del dispositivo o proprietario del profilo oppure un programma di installazione dei certificati con delega può chiamare removeKeyPair()
. Questa operazione rimuove un certificato e una coppia di chiavi private installati con un determinato alias di chiave privata.
Scenario di deployment
Utilizza questa funzionalità se un'organizzazione sta eseguendo la migrazione a una forma di certificato client più sicura. Se un amministratore implementa un nuovo certificato e la sua distribuzione richiede molto tempo, l'amministratore può revocare i certificati deprecati al termine della migrazione.
Reimpostazione del passcode di sicurezza
Il DPC può reimpostare la password di un utente autorizzando la modifica con un token sicuro preregistrato. I proprietari di dispositivi e i proprietari di profili possono chiamare API sicure per la reimpostazione del passcode per modificare rispettivamente la password dei dispositivi e dei profili di lavoro. La reimpostazione del passcode sicuro sostituisce resetPassword()
con i seguenti miglioramenti:
- Il DPC può reimpostare il passcode prima che l'utente sblocchi il dispositivo o il profilo dopo un riavvio sui dispositivi utilizzando la crittografia basata su file.
- L'archivio chiavi Android conserva le chiavi autenticate dall'utente dopo la reimpostazione del passcode.
Devi utilizzare la reimpostazione del passcode sicuro se la build DPC ha come target Android 8.0 (livello API 26) o versioni successive. La chiamata di resetPassword()
genera un elemento
SecurityException
nei DPC che hanno come target Android 8.0 o versioni successive, pertanto potrebbe
essere necessario aggiornare il DPC.
Impostare e attivare un token
Il DPC deve impostare e attivare un token prima di reimpostare una password. Dal momento che il DPC potrebbe non essere in grado di utilizzare subito il token, lo devi impostare prima del momento in cui un amministratore IT potrebbe averne bisogno.
Un token di reimpostazione della password è un valore casuale con una crittografia efficace e deve avere una lunghezza di almeno 32 byte. Crea un token per ogni dispositivo e profilo. Non riutilizzare o condividere i token generati.
Consigliamo di archiviare i token, o i mezzi per decriptare un token criptato, su un server. Se archivi i token localmente in un archivio criptato con credenziali, il DPC non può reimpostare la password finché l'utente non sblocca il dispositivo o il profilo. Se archivi i token localmente in uno spazio di archiviazione criptato del dispositivo, che viene compromesso, un utente malintenzionato potrebbe utilizzare il token per accedere a un profilo di lavoro o a un utente principale.
Puoi generare un nuovo token nel tuo DPC o recuperare un token da un server. L'esempio seguente mostra un DPC che genera un token e lo segnala a un server:
Kotlin
val token = ByteArray(32) // Generate a new token val random = SecureRandom() random.nextBytes(token) // Set the token to use at a later date val success: Boolean success = dpm.setResetPasswordToken(DeviceAdminReceiver.getComponentName(context), token) // Activate the token and update success variable... // Store the token on a server if (success) { sendTokenToServer(token) }
Java
byte token[] = new byte[32]; // Minimum size token accepted // Generate a new token SecureRandom random = new SecureRandom(); random.nextBytes(token); // Set the token to use at a later date boolean success; success = dpm.setResetPasswordToken(DeviceAdminReceiver.getComponentName(getContext()), token); // Activate the token and update success variable ... // Store the token on a server if (success) { sendTokenToServer(token); }
Nella maggior parte dei casi, il DPC deve attivare un token dopo averlo impostato. Tuttavia, quando l'utente non dispone di una password per la schermata di blocco, il sistema attiva subito un token. Per attivare un token, chiedi all'utente di confermare le sue credenziali.
Il DPC può chiamare il metodo KeyguardManager
createConfirmDeviceCredentialIntent()
per ottenere un Intent
che avvia la
conferma. Spiega all'utente del dispositivo nell'interfaccia utente il motivo per cui chiedi di eseguire l'autenticazione. Lo snippet seguente mostra come attivare un token nel tuo DPC:
Kotlin
// In your DPC, you'll need to localize the user prompt val ACTIVATE_TOKEN_PROMPT = "Use your credentials to enable remote password reset" val ACTIVATE_TOKEN_REQUEST = 1 // Create or fetch a token and set it in setResetPasswordToken() ... val keyguardManager = context.getSystemService(Context.KEYGUARD_SERVICE) as KeyguardManager val confirmIntent = keyguardManager.createConfirmDeviceCredentialIntent(null, ACTIVATE_TOKEN_PROMPT) if (confirmIntent != null) { startActivityForResult(confirmIntent, ACTIVATE_TOKEN_REQUEST) // Check your onActivityResult() callback for RESULT_OK } else { // Null means the user doesn't have a lock screen so the token is already active. // Call isResetPasswordTokenActive() if you need to confirm }
Java
// In your DPC, you'll need to localize the user prompt static final String ACTIVATE_TOKEN_PROMPT = "Use your credentials to enable remote password reset"; static final int ACTIVATE_TOKEN_REQUEST = 1; // Create or fetch a token and set it in setResetPasswordToken() ... KeyguardManager keyguardManager = (KeyguardManager) getSystemService(Context.KEYGUARD_SERVICE); Intent confirmIntent = keyguardManager.createConfirmDeviceCredentialIntent( null, ACTIVATE_TOKEN_PROMPT); if (confirmIntent != null) { startActivityForResult(confirmIntent, ACTIVATE_TOKEN_REQUEST); // Check your onActivityResult() callback for RESULT_OK } else { // Null means the user doesn't have a lock screen so the token is already active. // Call isResetPasswordTokenActive() if you need to confirm }
Devi attivare un token impostato dal DPC prima del riavvio del dispositivo. Android archivia un token non attivato in memoria e non lo memorizza in modo permanente dopo un riavvio. Se l'utente riavvia il dispositivo prima di attivare un token, il DPC può impostare di nuovo lo stesso token o generarne uno nuovo.
Il DPC può confermare che un token è attivo chiamando
isResetPasswordTokenActive()
e controllando che il risultato sia true
.
Una volta impostato e attivato un token, il DPC è valido fino a quando il DPC non elimina o sostituisce il token (o non vengono ripristinati i dati di fabbrica del dispositivo). Il token è indipendente dalla password e non viene interessato dalla modifica o dalla cancellazione della password da parte dell'utente.
Elimina un token
Puoi chiamare clearResetPasswordToken()
per eliminare un token impostato in precedenza dal tuo DPC. Potrebbe essere necessario revocare un token compromesso o potresti voler rimuovere
la possibilità di reimpostare la password. L'esempio seguente mostra come eseguire questa operazione
nel tuo DPC:
Kotlin
val dpm = getDpm() val admin = DeviceAdminReceiver.getComponentName(requireActivity()) // Clear the token if (!dpm.clearResetPasswordToken(admin)) { // Report the failure and possibly try later ... }
Java
DevicePolicyManager dpm = getDpm(); ComponentName admin = DeviceAdminReceiver.getComponentName(getActivity()); // Clear the token if (!dpm.clearResetPasswordToken(admin)) { // Report the failure and possibly try later ... }
Reimpostare la password
Quando un amministratore IT deve reimpostare la password, chiama
resetPasswordWithToken()
e trasmetti in anticipo il token impostato e attivato
dal DPC (controller criteri dispositivi):
Kotlin
val token: ByteArray = getTokenFromServer() val newPassword = "password" try { val result: Boolean = dpm.resetPasswordWithToken( DeviceAdminReceiver.getComponentName(requireContext()), newPassword, token, 0 ) if (result) { // The password is now 'password' } else { // Using 'password' doesn't meet password restrictions } } catch (e: IllegalStateException) { // The token doesn't match the one set earlier. }
Java
byte token[] = getTokenFromServer(); String newPassword = "password"; try { boolean result = dpm.resetPasswordWithToken( DeviceAdminReceiver.getComponentName(getContext()), newPassword, token, 0); if (result) { // The password is now 'password' } else { // Using `password` doesn't meet password restrictions } } catch (IllegalStateException e) { // The token doesn't match the one set earlier. }
Una chiamata a resetPasswordWithToken()
restituisce false
e la password
non cambia, se la nuova password non soddisfa i seguenti vincoli:
- Il numero di caratteri soddisfa i limiti di lunghezza minima delle password. Chiama il numero
getPasswordMinimumLength()
per sapere se un amministratore IT ha impostato un vincolo di lunghezza. - L'intervallo e la complessità dei caratteri nella password soddisfano un vincolo di composizione. Chiama
getPasswordQuality()
per sapere se un amministratore IT ha impostato un vincolo di composizione.
Se i vincoli di qualità delle password non richiedono l'impostazione di una password, puoi passare null
o una stringa vuota a resetPasswordWithToken()
per rimuovere la password.
Verifica della sicurezza del profilo di lavoro
Un DPC eseguito in modalità proprietario del profilo può richiedere agli utenti di specificare una verifica di sicurezza per le app in esecuzione nel profilo di lavoro. Il sistema mostra la verifica di sicurezza quando l'utente tenta di aprire un'app di lavoro. Se l'utente completa correttamente la verifica di sicurezza, il sistema sblocca il profilo di lavoro e, se necessario, lo decripta.
Come funziona la verifica della sicurezza del profilo di lavoro
- Se un DPC invia un intent
ACTION_SET_NEW_PASSWORD
, il sistema chiede all'utente di impostare una verifica di sicurezza. - Il DPC può anche inviare un'intent
ACTION_SET_NEW_PARENT_PROFILE_PASSWORD
per richiedere all'utente di impostare un blocco del dispositivo.
Un DPC può impostare i criteri relativi alle password per la verifica di lavoro in modo diverso rispetto ai criteri per le altre password dei dispositivi. Ad esempio, la lunghezza minima per la risposta di verifica del dispositivo può essere diversa da quella richiesta per altre password. Un DPC imposta i criteri della verifica utilizzando i consueti metodi DevicePolicyManager
, come setPasswordQuality()
e setPasswordMinimumLength()
.
considerazioni
- Il DPC può reimpostare la password sul profilo di lavoro, ma non può reimpostare la password (personale) del dispositivo. Se un utente sceglie di impostare la stessa password per il lavoro e per quella personale, la password
resetPassword()
nel profilo di lavoro viene reimpostata solo sul profilo di lavoro e la password non sarà la stessa della schermata di blocco del dispositivo. - Un DPC può personalizzare la schermata delle credenziali per la sfida di lavoro utilizzando
setOrganizationColor()
esetOrganizationName()
. - Gli amministratori dei dispositivi non possono utilizzare
resetPassword()
per cancellare le password o cambiare quelle già impostate. Gli amministratori del dispositivo possono comunque impostare una password, ma solo se il dispositivo non ha password, PIN o sequenza.
Per saperne di più, consulta getParentProfileInstance()
e la documentazione di riferimento in DevicePolicyManager
.