Melhorar a segurança com políticas de gerenciamento de dispositivos

Suspensão de uso do administrador do dispositivo. Algumas políticas de administrador foram marcadas como descontinuadas quando invocadas por um administrador do dispositivo. Para saber mais e ver as opções de migração, consulte Descontinuação do administrador do dispositivo.

Desde o Android 2.2 (API de nível 8), a plataforma Android oferece gerenciamento de dispositivos em nível de sistema por meio das APIs de administração de dispositivos.

Nesta lição, você vai aprender a criar um aplicativo com reconhecimento de segurança que gerencia o acesso aplicando políticas de gerenciamento de dispositivos. Especificamente, o aplicativo pode ser configurado de modo que uma senha de bloqueio de tela com nível suficiente seja configurada antes da exibição conteúdo restrito ao usuário.

Definir e declarar sua política

Primeiro, defina os tipos de política com suporte no nível funcional. As políticas podem abrange o nível da senha do bloqueio de tela, o tempo limite de expiração, a criptografia etc.

Você precisa declarar o conjunto de políticas selecionado, que será aplicado pelo aplicativo, no res/xml/device_admin.xml. O manifesto do Android também precisa referenciar o um conjunto de políticas declaradas.

Cada política declarada corresponde a um certo número de métodos de política de dispositivo relacionados no DevicePolicyManager, definindo o tamanho mínimo da senha e o número mínimo de caracteres maiúsculos são dois exemplos). Se um aplicativo tentar invocar métodos cuja uma política correspondente não for declarada no XML, o que vai resultar em uma SecurityException no momento da execução. Outras permissões, como force-lock, estarão disponíveis se o aplicativo pretende gerenciar e outros tipos de política. Como você verá mais tarde, como parte do processo de ativação do administrador do dispositivo, a lista de políticas declaradas vai aparecer para o usuário em uma tela do sistema.

O snippet abaixo declara a política de senha de limite em res/xml/device_admin.xml:

<device-admin xmlns:android="http://schemas.android.com/apk/res/android">
    <uses-policies>
        <limit-password />
    </uses-policies>
</device-admin>

XML de declaração de política referenciado no manifesto do Android:

<receiver android:name=".Policy$PolicyAdmin"
    android:permission="android.permission.BIND_DEVICE_ADMIN">
    <meta-data android:name="android.app.device_admin"
        android:resource="@xml/device_admin" />
    <intent-filter>
        <action android:name="android.app.action.DEVICE_ADMIN_ENABLED" />
    </intent-filter>
</receiver>

Criar um receptor de administração de dispositivo

Crie um broadcast receiver de administração de dispositivos, que recebe notificações sobre eventos relacionados às políticas que você declarou oferecer suporte. Um aplicativo pode modificar seletivamente os métodos de callback.

No aplicativo de exemplo, "Administrador do dispositivo", quando o administrador do dispositivo é desativado pelo usuário, a política configurada será apagada da preferência compartilhada. Considere a implementação lógica de negócios que seja relevante para o caso de uso. Por exemplo, o aplicativo pode levar algumas ações para mitigar os riscos de segurança implementando uma combinação de exclusão de dados sensíveis na dispositivo, desabilitação da sincronização remota, alerta um administrador, etc.

Para que o broadcast receiver funcione, registre-o no manifesto do Android, conforme ilustrado no snippet acima.

Kotlin

class PolicyAdmin : DeviceAdminReceiver() {

    override fun onDisabled(context: Context, intent: Intent) {
        // Called when the app is about to be deactivated as a device administrator.
        // Deletes previously stored password policy.
        super.onDisabled(context, intent)
        context.getSharedPreferences(APP_PREF, Activity.MODE_PRIVATE).edit().apply {
            clear()
            apply()
        }
    }
}

Java

public static class PolicyAdmin extends DeviceAdminReceiver {

    @Override
    public void onDisabled(Context context, Intent intent) {
        // Called when the app is about to be deactivated as a device administrator.
        // Deletes previously stored password policy.
        super.onDisabled(context, intent);
        SharedPreferences prefs = context.getSharedPreferences(APP_PREF, Activity.MODE_PRIVATE);
        prefs.edit().clear().commit();
    }
}

Ativar o administrador do dispositivo

Antes de aplicar qualquer política, o usuário precisa ativar manualmente o aplicativo como um dispositivo administrador. O snippet abaixo ilustra como acionar a atividade de configurações na qual o usuário possa ativar seu aplicativo. É recomendável incluir o texto explicativo para destacar aos usuários por que o aplicativo está solicitando para ser um administrador de dispositivo, especificando o EXTRA_ADD_EXPLANATION a mais na intent.

Figura 1. A tela de ativação do usuário, na qual é possível fornecer uma descrição das políticas do dispositivo.

Kotlin

if (!policy.isAdminActive()) {

    val activateDeviceAdminIntent = Intent(DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN)

    activateDeviceAdminIntent.putExtra(
            DevicePolicyManager.EXTRA_DEVICE_ADMIN,
            policy.getPolicyAdmin()
    )

    // It is good practice to include the optional explanation text to
    // explain to user why the application is requesting to be a device
    // administrator. The system will display this message on the activation
    // screen.
    activateDeviceAdminIntent.putExtra(
            DevicePolicyManager.EXTRA_ADD_EXPLANATION,
            resources.getString(R.string.device_admin_activation_message)
    )

    startActivityForResult(activateDeviceAdminIntent, REQ_ACTIVATE_DEVICE_ADMIN)
}

Java

if (!policy.isAdminActive()) {

    Intent activateDeviceAdminIntent =
        new Intent(DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN);

    activateDeviceAdminIntent.putExtra(
        DevicePolicyManager.EXTRA_DEVICE_ADMIN,
        policy.getPolicyAdmin());

    // It is good practice to include the optional explanation text to
    // explain to user why the application is requesting to be a device
    // administrator. The system will display this message on the activation
    // screen.
    activateDeviceAdminIntent.putExtra(
        DevicePolicyManager.EXTRA_ADD_EXPLANATION,
        getResources().getString(R.string.device_admin_activation_message));

    startActivityForResult(activateDeviceAdminIntent,
        REQ_ACTIVATE_DEVICE_ADMIN);
}

Se o usuário escolher "Ativar", o aplicativo se torna um administrador do dispositivo e pode começar configuração e aplicação da política.

O aplicativo também precisa estar preparado para lidar com situações de abandono em que o usuário abandona o processo de ativação pressionando o botão Cancelar, a tecla Voltar ou a tecla Home. Portanto, O onResume() na atividade de configuração de políticas precisa ter lógica. para reavaliar a condição e apresentar a opção de ativação do administrador do dispositivo se necessários.

Implementar o controlador de política de dispositivo

Depois que o administrador do dispositivo é ativado, o aplicativo configura o dispositivo Gerenciador de políticas com a política solicitada. Lembre-se de que novas políticas estão sendo adicionadas Android a cada versão. É apropriado realizar verificações de versão em seu aplicativo se você estiver usando novas políticas, além de oferecer suporte a versões mais antigas da plataforma. Por exemplo, o Mínimo de Senha A política de maiúsculas e minúsculas está disponível apenas no nível 11 da API (Honeycomb) e mais recentes. O código a seguir demonstra como verificar a versão durante a execução.

Kotlin

private lateinit var dpm: DevicePolicyManager
private lateinit var policyAdmin: ComponentName

dpm = context.getSystemService(Context.DEVICE_POLICY_SERVICE) as DevicePolicyManager
policyAdmin = ComponentName(context, PolicyAdmin::class.java)

dpm.apply {
    setPasswordQuality(policyAdmin, PASSWORD_QUALITY_VALUES[passwordQuality])
    setPasswordMinimumLength(policyAdmin, passwordLength)
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
        setPasswordMinimumUpperCase(policyAdmin, passwordMinUpperCase)
    }
}

Java

DevicePolicyManager dpm = (DevicePolicyManager)
        context.getSystemService(Context.DEVICE_POLICY_SERVICE);
ComponentName policyAdmin = new ComponentName(context, PolicyAdmin.class);

dpm.setPasswordQuality(policyAdmin, PASSWORD_QUALITY_VALUES[passwordQuality]);
dpm.setPasswordMinimumLength(policyAdmin, passwordLength);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB) {
    dpm.setPasswordMinimumUpperCase(policyAdmin, passwordMinUpperCase);
}

Nesse ponto, o aplicativo pode aplicar a política. Enquanto o aplicativo não tem acesso com a senha real de bloqueio de tela usada, ele pode determinar pela API Device Policy Manager se a senha atende à política exigida. Se o processo atual senha de bloqueio de tela não é suficiente, a API de administração do dispositivo não leva e ações corretivas. É responsabilidade do aplicativo iniciar o sistema explicitamente tela de alteração de senha no app Configurações. Por exemplo:

Kotlin

if (!dpm.isActivePasswordSufficient) {
    // Triggers password change screen in Settings.
    Intent(DevicePolicyManager.ACTION_SET_NEW_PASSWORD).also { intent ->
        startActivity(intent)
    }
}

Java

if (!dpm.isActivePasswordSufficient()) {
    ...
    // Triggers password change screen in Settings.
    Intent intent =
        new Intent(DevicePolicyManager.ACTION_SET_NEW_PASSWORD);
    startActivity(intent);
}

Normalmente, o usuário pode selecionar um dos mecanismos de bloqueio disponíveis, como "Nenhum", "Padrão" PIN (numérico) ou senha (alfanumérica). Quando uma política de senha é configurada, essas senhas os tipos mais fracos do que os definidos na política são desativados. Por exemplo, se o A qualidade da senha “numérica” está configurada, o usuário pode selecionar PIN (numérico) ou senha (alfanumérica).

Assim que o dispositivo estiver devidamente protegido por meio da configuração de uma senha de bloqueio de tela adequada, o aplicativo permite o acesso ao conteúdo protegido.

Kotlin

when {
    !dpm.isAdminActive(policyAdmin) -> {
        // Activates device administrator.
        ...
    }
    !dpm.isActivePasswordSufficient -> {
        // Launches password set-up screen in Settings.
        ...
    }
    else -> {
        // Grants access to secure content.
        ...
        startActivity(Intent(context, SecureActivity::class.java))
    }
}

Java

if (!dpm.isAdminActive(..)) {
    // Activates device administrator.
    ...
} else if (!dpm.isActivePasswordSufficient()) {
    // Launches password set-up screen in Settings.
    ...
} else {
    // Grants access to secure content.
    ...
    startActivity(new Intent(context, SecureActivity.class));
}