Rede e telefonia

Os recursos deste guia descrevem o gerenciamento de rede e telefonia que você pode implementar na política do dispositivo Controller (DPC). Este documento contém código de amostra, e você também pode usar o recurso Testar app de DPC como um uma fonte de exemplos de código para os recursos empresariais do Android.

Um app de DPC pode ser executado no modo "Proprietário do perfil" em dispositivos pessoais ou no proprietário do dispositivo em dispositivos totalmente gerenciados. Esta tabela indica quais atributos são disponível quando o DPC é executado no modo de proprietário do perfil ou proprietário do dispositivo modo:

Recurso Proprietário do perfil Proprietário do dispositivo
Acessar contatos de trabalho entre perfis
Garanta uma conexão de rede segura para o tráfego de trabalho
Configure um um único ID de rede sem fio entre regiões
Especifique discador separado para o perfil de trabalho

Acessar contatos de trabalho em vários perfis

Os EMMs podem permitir que o perfil pessoal de um usuário acesse os contatos de trabalho para que os contatos pessoais e profissionais de um usuário podem ser acessados por meio de pesquisa local e busca de diretório remoto. Em dispositivos pessoais, um único discador na pode fazer e receber chamadas pessoais e de trabalho. Além disso, e os contatos de trabalho estão bem integrados à UI do sistema. Se o perfil de trabalho for criptografados, os dados não ficam disponíveis para o perfil pessoal.

Integrado com a interface do sistema

A interface do sistema indica o recebimento de chamadas de trabalho usando um ícone de pasta. A callLog também mostra para designar chamadas de trabalho recebidas e efetuadas. O discador pessoal os apps de contatos podem mostrar as informações do identificador de chamadas de um contato de trabalho usando um controle remoto do Google, por isso não é necessário que o contato já esteja sincronizado na dispositivo local. O app de mensagens pode fazer pesquisas e identificação de chamadas locais.

A Definição de compatibilidade do Android Documento (CDD) inclui requisitos para que os contatos de trabalho apareçam no discador padrão e os requisitos que contatos e aplicativos de mensagens recebem selos para indicar que são do trabalho perfil.

Os contatos de trabalho são acessíveis e pesquisáveis

O usuário pode acessar e ligar para contatos de trabalho pelo perfil pessoal, que aparecer na tela de pesquisa do aplicativo discador. O usuário pode pesquisar trabalho contatos (usando o preenchimento automático), que são sincronizados localmente com o dispositivo e listados usando uma pesquisa de diretório remoto.

Controlar contatos de trabalho no perfil principal

O DPC controla a permissão para pesquisar contatos de trabalho. Em execução no proprietário do perfil o DPC gerencia a visibilidade dos contatos de trabalho no perfil pessoal. Para mais informações, consulte Criar uma política do dispositivo Controller (link em inglês).

A pesquisa de contatos de trabalho pelo perfil pessoal está ativada por padrão.

Garantir uma conexão de rede segura para o tráfego de trabalho

Em execução no modo "Proprietário do dispositivo" ou "Proprietário do perfil", uma política do dispositivo pode usar uma conexão de rede privada virtual (VPN) sempre ativa para forçam os aplicativos a transmitir tráfego por um app de VPN específico que não pode ser pode ser ignorado. Usando uma conexão VPN sempre ativa, o DPC pode garantir o tráfego de um perfil de trabalho ou dispositivo gerenciado passa por um serviço de VPN; sem a intervenção dos usuários. Esse processo cria uma conexão de rede segura para contínuo em um perfil de trabalho.

Sobre conexões VPN sempre ativas

Como parte do framework do sistema, o roteamento da VPN é gerenciado automaticamente para que o usuário não poderá ignorar o serviço de VPN. Se o serviço de VPN estiver desconectado durante modo de bloqueio total, o tráfego não poderá vazar para a Internet aberta. Para aplicativos implementar VpnService, a VPN sempre ativa oferece um framework para gerenciar uma conexão VPN segura por meio de em um servidor confiável e mantê-lo ativo. O serviço de VPN reinicia automaticamente conexão em todas as atualizações de apps, independentemente de a conexão ser por Wi-Fi ou rede celular. Se o dispositivo for reinicializado, o framework reiniciará a conexão VPN.

A conexão com o serviço de VPN é transparente para o usuário. Para um dispositivo da empresa, o usuário não precisa confirmar a caixa de diálogo de consentimento de um VPN no modo sempre ativo. As configurações de rede VPN do usuário permitem ativar uma sempre ativada manualmente.

Se DISALLOW_CONFIG_VPN for true, o usuário é impedido de configurar a VPN. Ativar DISALLOW_DEBUGGING_FEATURES para impedir que os usuários substituam a VPN sempre ativa usando o comando adb debug. Para impedir que um usuário desinstale a VPN, chame DevicePolicyManager.setUninstallBlocked:

Configurar o serviço de VPN

A organização que usa sua solução empresarial para Android configura uma VPN.

  1. Instale um app de VPN que implemente VpnService: É possível encontrar serviços de VPN ativos usando um filtro de intent que corresponda ao ação VpnService.SERVICE_INTERFACE:
  2. Declare um VpnService no manifesto do app protegido pela permissão BIND_VPN_SERVICE.
  3. Configure o VpnService para que ele seja iniciado pelo sistema. Evite configurar o app de VPN para iniciar automaticamente detectar a inicialização do sistema e controlar o próprio ciclo de vida.
  4. Defina o papel gerenciado personalizadas para o app de VPN (veja o exemplo abaixo).

Ativar a conexão VPN sempre ativa

O DPC pode configurar uma conexão VPN sempre ativa por meio de um app específico chamar DevicePolicyManager.setAlwaysOnVpnPackage():

Essa conexão é concedida automaticamente e persiste após a reinicialização. Se lockdownEnabled for falso, o tráfego de rede pode não estar seguro a partir do momento em que o smartphone é reinicializado e a VPN é conectada. Isso é útil se você não quiser parar conectividade de rede sempre que uma VPN falha ou se a VPN não é essencial.

Verificar a conexão VPN sempre ativa

O DPC pode ler o nome do pacote que administra uma VPN sempre ativa uma conexão com a Internet para o usuário atual DevicePolicyManager.getAlwaysOnVpnPackage().

Se não houver um pacote desse tipo ou se a VPN tiver sido criada nas configurações do sistema app, null será retornado.

Exemplo

No app TestDPC, o AlwaysOnVpnFragment.java usa essas APIs para ativar a configuração de uma conexão VPN sempre ativa.

No exemplo a seguir:

  • O papel gerenciado personalizadas do VPN do Google Cloud são definidos pelo DevicePolicyManager usando seu setApplicationRestrictions() .
  • As configurações gerenciadas usam pares de chave-valor arbitrários e este app de exemplo os usa em outro lugar para definir as configurações de rede da VPN (consulte Verificar configurações gerenciadas).
  • O exemplo adiciona o instalador do pacote do Android a uma lista de bloqueio para que ele não atualizar os pacotes do sistema pela VPN. Todo o tráfego de rede do usuário no o dispositivo ou perfil de trabalho passa por esse app de VPN, exceto o pacote instalador e as atualizações dele usam a Internet aberta.
  • Em seguida, o DevicePolicyManager ativa a conexão VPN sempre ativa para o um pacote de VPN usando setAlwaysOnVpnPackage(), e ativar o modo de bloqueio total.

Kotlin

// Set VPN's managed configurations
val config = Bundle().apply {
  putString(Extras.VpnApp.ADDRESS, "192.0.2.0")
  putString(Extras.VpnApp.IDENTITY, "vpn.account1")
  putString(Extras.VpnApp.CERTIFICATE, "keystore://auth_certificate")
  putStringArray(Extras.VpnApp.DENYLIST,
        arrayOf("com.android.packageinstaller"))
}

val dpm = getSystemService(Context.DEVICE_POLICY_SERVICE) as DevicePolicyManager

val admin = myDeviceAdminReceiver.getComponentName(this)

// Name of package to update managed configurations
val vpnPackageName = "com.example.vpnservice"

// Associate managed configurations with DeviceAdminReceiver
dpm.setApplicationRestrictions(admin, vpnPackageName, config)

// Enable always-on VPN connection through VPN package
try {
  val lockdownEnabled = true
  dpm.setAlwaysOnVpnPackage(admin, vpnPackageName, lockdownEnabled)
} catch (ex: Exception) {
  throw PolicyException()
}

Java

// Set VPN's managed configurations
final Bundle config = new Bundle();
config.putString(Extras.VpnApp.ADDRESS, "192.0.2.0");
config.putString(Extras.VpnApp.IDENTITY, "vpn.account1");
config.putString(Extras.VpnApp.CERTIFICATE, "keystore://auth_certificate");
config.putStringArray(Extras.VpnApp.DENYLIST,
                      new String[]{"com.android.packageinstaller"});

DevicePolicyManager dpm = (DevicePolicyManager) getSystemService(Context.DEVICE_POLICY_SERVICE);

ComponentName admin = myDeviceAdminReceiver.getComponentName(this);

// Name of package to update managed configurations
final String vpnPackageName = "com.example.vpnservice";

// Associate managed configurations with DeviceAdminReceiver
dpm.setApplicationRestrictions(admin, vpnPackageName, config);

// Enable always-on VPN connection through VPN package
try {
  boolean lockdownEnabled = true;
  dpm.setAlwaysOnVpnPackage(admin, vpnPackageName, lockdownEnabled));
} catch (Exception ex) {
  throw new PolicyException(...);
}

Configurar um único ID de rede sem fio em várias regiões

Em execução no modo "Proprietário do dispositivo" ou "Proprietário do perfil", uma política do dispositivo de controle de acesso (DPC) pode associar vários certificados de autoridade de certificação (CA) com uma única rede sem fio. Com essa configuração, um dispositivo possam se conectar a pontos de acesso sem fio que tenham o mesmo nome de rede ou identificador do conjunto de serviços (SSID), mas estão configurados com CAs diferentes. certificados. Isso é útil quando as redes sem fio da sua organização em diversas regiões geográficas, e cada região exige uma região autoridade certificadora. Por exemplo, assinaturas legais podem exigir uma assinatura uma autoridade certificadora que precisa de uma AC regional.

Observação: o Android tem suporte setCaCertificate desde a API 18 (Jelly Bean), mas os administradores de TI precisam provisionar as redes. separadamente com cada CA para garantir que os dispositivos tenham autenticação perfeita em cada de acesso, independentemente da região.

Especificar certificados de CA para identificar o servidor

Para especificar uma lista de certificados X.509 que identificam o servidor usando a mesma SSID, inclua todas as CAs relevantes na configuração sem fio usando WifiEnterpriseConfig.setCaCertificates().

O certificado de um servidor será válido se a CA dele corresponder a um dos certificados fornecidos. Os nomes padrão são atribuídos automaticamente aos certificados e usados no configuração do Terraform. A WifiManager instala o certificado e salva a configuração automaticamente quando está ativada e remove o certificado quando a configuração é excluída.

Para obter todos os certificados de CA associados à configuração sem fio, use WifiEnterpriseConfig.getCaCertificates() para retornar uma lista de objetos X509Certificate.

Adicionar uma configuração sem fio usando vários certificados de CA

  1. Verifique a identidade do servidor:
    1. Carregue os certificados de CA X.509.
    2. Carregue a chave privada e o certificado do cliente. Consulte Segurança com HTTPS e SSL para um exemplo de como ler um arquivo de certificado.
  2. Criar um novo WifiConfiguration e definir o SSID (Identificador do conjunto de serviços) e o gerenciamento de chaves.
  3. Configure o WifiEnterpriseConfig instância neste WifiConfiguration.
    1. Identifique o servidor com uma lista de X509Certificate objetos usando setCaCertificates().
    2. Defina as credenciais, a identidade e a senha do cliente.
    3. Defina o Protocolo de autenticação extensível (EAP) e o método da fase 2 como para estabelecer a conexão.
  4. Adicione a rede com a função WifiManager:
  5. Ativar a rede. O WifiManager salva a configuração automaticamente durante configuração da infraestrutura.

Este exemplo reúne as etapas em um só lugar:

Kotlin

// Verify the server's identity
val caCert0 = getCaCert("cert0.crt")
val caCert1 = getCaCert("cert1.crt")
val clientKey = getClientKey()
val clientCert = getClientCert()

// Create Wi-Fi configuration
val wifiConfig = WifiConfiguration().apply {
  SSID = "mynetwork"
  allowedKeyManagement.set(KeyMgmt.WPA_EAP)
  allowedKeyManagement.set(KeyMgmt.IEEE8021X)

  // Set up Wi-Fi enterprise configuration
  enterpriseConfig.setCaCertificates(arrayOf<X509Certificate>(caCert0, caCert1))
  enterpriseConfig.setClientKeyEntry(clientKey, clientCert)
  enterpriseConfig.setIdentity("myusername")
  enterpriseConfig.setEapMethod(Eap.TLS)
  enterpriseConfig.setPhase2Method(Phase2.NONE)
}


// Add network
val wifiManager = getSystemService(Context.WIFI_SERVICE) as WifiManager
val netId = wifiManager.addNetwork(wifiConfig)

// Enable network
if (netId < 0) {
  // Error creating new network
} else {
  wifiManager.enableNetwork(netId, true)
}

Java

// Verify the server's identity
X509Certificate caCert0 = getCaCert("cert0.crt");
X509Certificate caCert1 = getCaCert("cert1.crt");
PrivateKey clientKey = getClientKey();
X509Certificate clientCert = getClientCert();

// Create Wi-Fi configuration
WifiConfiguration wifiConfig = new WifiConfiguration();
wifiConfig.SSID = "mynetwork";
wifiConfig.allowedKeyManagement.set(KeyMgmt.WPA_EAP);
wifiConfig.allowedKeyManagement.set(KeyMgmt.IEEE8021X);

// Set up Wi-Fi enterprise configuration
wifiConfig.enterpriseConfig.setCaCertificates(new X509Certificate[] {caCert0, caCert1});
wifiConfig.enterpriseConfig.setClientKeyEntry(clientKey, clientCert);
wifiConfig.enterpriseConfig.setIdentity("myusername");
wifiConfig.enterpriseConfig.setEapMethod(Eap.TLS);
wifiConfig.enterpriseConfig.setPhase2Method(Phase2.NONE);

// Add network
WifiManager wifiManager = (WifiManager) getSystemService(Context.WIFI_SERVICE);
int netId = wifiManager.addNetwork(wifiConfig);

// Enable network
if (netId < 0) {
  // Error creating new network
} else {
  wifiManager.enableNetwork(netId, true);
}

Especificar um discador separado para o perfil de trabalho

Você pode colocar um aplicativo discador separado na lista de permissões para ser usado em um perfil de trabalho. Pode ser o próprio discador ou um aplicativo de voz sobre IP (VoIP) que implemente a ConnectionService API para o back-end de chamada. Isso fornece a mesma discagem da interface do sistema integrado experiência em aplicativos VoIP no perfil de trabalho, o que torna o trabalho o discador é um recurso principal. As chamadas recebidas para as contas de trabalho são diferente das chamadas recebidas para as contas de chamadas pessoais.

O usuário pode optar por fazer e receber ligações no discador de trabalho na lista de permissões em uma conta de telefone. Todas as ligações feitas desse discador ou recebidas para o trabalho de usuário final, são gravadas no arquivo CallLog de nuvem. O discador de trabalho mantém um registro de chamadas somente para o trabalho, com acesso apenas ao contatos de trabalho. As chamadas de comutação recebidas são gerenciadas pelo discador principal e armazenados em um registro de chamadas pessoal. Se um perfil de trabalho for excluído, o registro de chamadas associados a esse perfil de trabalho também serão excluídos, assim como todos os perfis de trabalho dados.

Os apps de terceiros precisam implementar ConnectionService

Apps VoIP de terceiros que precisam fazer e receber ligações telefônicas integrado ao aplicativo de celular integrado pode implementar a ConnectionService API. Isso é necessário para qualquer serviço VoIP usado para chamadas de trabalho. Esses apps ter as chamadas tratadas como chamadas móveis tradicionais, por por exemplo, elas aparecem no discador do sistema integrado e no registro de chamadas. Se o implementação de app ConnectionService está instalado no perfil de trabalho, só pode ser acessado por um discador instalado nesse perfil de trabalho.

Depois que o desenvolvedor tiver implementado ConnectionService, eles devem adicioná-lo ao arquivo de manifesto do aplicativo e registrar um PhoneAccount com o TelecomManager Uma conta telefônica representa um método distinto para fazer ou receber chamadas telefônicas, e pode haver vários PhoneAccounts para cada ConnectionService. Depois de registrar a conta telefônica, pode ativá-la nas configurações do discador.

Notificações e integração da interface do sistema

A interface do sistema oferece aos usuários uma experiência de discagem consistente e integrada. para apps de terceiros que usam o ConnectionService como back-end para fazer chamadas. Se estiver usando o app em um perfil de trabalho, use uma pasta é exibido nas chamadas recebidas e na barra de status. Um app que implementa O ConnectionService instalado no perfil de trabalho pode usar o discador do sistema ou criar um discador de trabalho separado. Eles podem ser um único app apps separados.

O aplicativo discador determina se está fazendo ou recebendo uma chamada de trabalho pelo verificação da flag android.telecom.Call.Details.PROPERTY_ENTERPRISE_CALL: Se for uma chamada de trabalho, o discador indica isso para o usuário adicionando uma crachá (ícone de pasta):

Kotlin

// Call placed through a work phone account. getCurrentCall() is defined by the
// dialer.
val call = getCurrentCall()
if (call.hasProperty(android.telecom.Call.Details.PROPERTY_ENTERPRISE_CALL)) {
  // Set briefcase icon
}

Java

// Call placed through a work phone account. getCurrentCall() is defined by the
// dialer.
Call call = getCurrentCall();
if (call.hasProperty(android.telecom.Call.Details.PROPERTY_ENTERPRISE_CALL)) {
  // Set briefcase icon
}