Vídeo
Dev Byte: Novidades do Android 5.0
Vídeo
Dev Byte: Notificações
Nível da API: 21
Junto com novos recursos e funcionalidades, o Android N inclui uma série de mudanças de comportamento do sistema e da API. Este documento destaca algumas das principais mudanças que você deve entender e considerar nos aplicativos.
Caso tenha publicado anteriormente um aplicativo para Android, saiba que ele pode ser afetado essas alterações ao Android 5.0.
Para obter uma visão mais detalhada dos novos recursos de plataforma, dê uma olhada em destaques do Android Lollipop.
Android Runtime (ART)
No Android 5.0, o tempo de execução ART substitui o Dalvik como a plataforma padrão. O tempo de execução ART foi introduzido no Android 4.4 de forma experimental.
Para conhecer os novos recursos do ART, veja Introdução ao ART. Alguns dos principais novos recursos são:
- Compilação antecipada (AOT)
- Melhor coleta de lixo (GC)
- Melhor suporte à depuração
A maioria dos aplicativos Android devem funcionar normalmente sem precisar mudar nada no ART. No entanto, algumas técnicas que funcionam no Dalvik não funcionam no ART. Para saber mais sobre os problemas mais importantes, consulte Verificação do comportamento do aplicativo no Android Runtime (ART) Dê atenção especial se:
- Se aplicativo usar Java Native Interface (JNI) para executar código C/C++.
- Você usar ferramentas de desenvolvimento que geram código não padrão (como alguns ofuscadores).
- Você usar técnicas incompatíveis com a compactação da coleta de lixo.
Notificações
Certifique-se de que suas notificações levam essas mudanças ao Android 5.0 em consideração. Para saber mais sobre projetar notificações para Android 5.0 e posteriores, consulte o guia de criação de notificações.
Estilo do material design
As notificações são desenhadas em texto escuro sobre fundos brancos (ou muito claros) para combinar com os novos widgets do material design. Veja se todas as notificações ficam com o visual certo com o novo esquema de cores. Se as notificações tiverem visual errado, conserte-as:
- Use
setColor()
para definir um cor de realce em um círculo atrás da imagem do ícone. - Atualize ou remova ativos que envolvam cor. O sistema ignora todos os canais não alfa em ícones de ação e no ícone de notificação principal. Você deve presumir que esses ícones serão somente alfa. O sistema desenha ícones de notificação e ícones de ação em cinza escuro.
Som e vibração
Se você estiver adicionando sons e vibrações às notificações usando as classes Ringtone
, MediaPlayer
ou Vibrator
, remova esse código para que o sistema possa apresentar as notificações em modo priority corretamente. Em vez delas, use os métodos Notification.Builder
para adicionar som e vibração.
Definir o dispositivo como RINGER_MODE_SILENT
faz com que ele entre no novo modo de prioridade. O dispositivo sairá do modo de prioridade se você o definir como RINGER_MODE_NORMAL
ou RINGER_MODE_VIBRATE
.
No passado, o Android usava STREAM_MUSIC
como o fluxo principal para controlar o volume em tablets. No Android 5.0, o fluxo de volume principal, tanto para celulares quanto para tablets, agora está unificado e é controlado por STREAM_RING
ou STREAM_NOTIFICATION
.
Visibilidade na tela de bloqueio
Por padrão, agora as notificações aparecem na tela de bloqueio no Android 5.0. Os usuários podem escolher proteger informações sigilosas contra a exposição e, nesse caso, o sistema editará o texto exibido pela notificação. Para personalizar essa notificação editada, use setPublicVersion()
.
Se a notificação não contiver informações pessoais, ou se você quiser oferecer controle sobre a reprodução de mídia na notificação, chame o método setVisibility()
e defina o nível de visibilidade da notificação como VISIBILITY_PUBLIC
.
Reprodução de mídia
Se estiver implementando notificações que apresentem o status atual da reprodução de mídia ou transportem controles, considere usar o novo modelo de Notification.MediaStyle
em vez de um objeto RemoteViews.RemoteView
personalizado. Independentemente da abordagem que escolher, não deixe de definir a visibilidade da notificação como VISIBILITY_PUBLIC
para que os controles possam ser acessados na tela de bloqueio. Observe que, a partir do Android 5.0, o sistema não exibe mais objetos RemoteControlClient
na tela de bloqueio. Para saber mais, consulte Se seu aplicativo usa RemoteControlClient.
Notificação de informações básicas
As notificações agora podem aparecer em uma janela flutuante pequena (também chamada de notificação de informações básicas) quando o dispositivo está ativo (ou seja, está desbloqueado ou sua tela está acesa). Essas notificações aparecem de maneira semelhante à forma compacta da notificação, exceto que a notificação de informações básicas também exibe botões de ação. Os usuários podem realizar uma ação ou descartar uma notificação de informações básicas sem sair do aplicativo atual.
Exemplos de condições que podem ativar uma notificação de informações básicas incluem:
- A atividade do usuário está em modo de tela cheia (o aplicativo usa
fullScreenIntent
) - A notificação tem alta prioridade e usa toques ou vibrações
Se seu aplicativo implementar notificações em qualquer um desses cenários, certifique-se de que as notificações de informações básicas sejam apresentadas corretamente.
Controles de mídia e RemoteControlClient
A classe RemoteControlClient
agora está obsoleta. Troque para a nova MediaSession
API assim que possível.
As telas de bloqueio no Android 5.0 não mostram controles de transporte para MediaSession
nem para RemoteControlClient
. Em vez disso, seu aplicativo pode fornecer controle de reprodução de mídia na tela de bloqueio por meio de uma notificação. Isso dá ao aplicativo mais controle sobre a apresentação dos botões de mídia e ainda fornece uma experiência consistente aos usuários em dispositivos bloqueados e desbloqueados.
Para tanto, o Android 5.0 apresenta um novo modelo Notification.MediaStyle
. O Notification.MediaStyle
converte ações de notificação, que você adicionou com Notification.Builder.addAction()
, em botões compactos integrados às notificações de reprodução de mídia do aplicativo. Passe o token da sua sessão ao método setSession()
para informar o sistema de que essa notificação controla uma sessão de mídia em andamento.
Não se esqueça de definir a visibilidade da notificação como VISIBILITY_PUBLIC
para marcar a notificação como segura para exibição em qualquer tela de bloqueio (protegida ou similar). Para saber mais, consulte Notificações na tela de bloqueio.
Para exibir controles de reprodução de mídia se o aplicativo estiver em execução na plataforma Android TV ou no Wear, implemente a classe MediaSession
. Você também deve implementar MediaSession
se o aplicativo precisar receber eventos de botão de mídia em dispositivos Android.
getRecentTasks()
Com a introdução do novo recurso de tarefas de atividades e documentos simultâneos no Android 5.0 (veja Atividades e documentos simultâneos na tela de recentes abaixo), o método ActivityManager.getRecentTasks()
agora está obsoleto para aumentar a privacidade do usuário. Para compatibilidade retroativa, esse método ainda retorna um pequeno subconjunto de seus dados, incluindo a chamada de tarefas próprias do aplicativo e possivelmente algumas outras não sigilosas (como Tela inicial). Se seu aplicativo estiver usando esse método para recuperar as próprias tarefas, use getAppTasks()
em vez de recuperar essas informações.
Compatibilidade com 64 bits do Android NDK
O Android 5.0 introduz a compatibilidade com sistemas de 64 bits. A melhoria com os 64 bits aumenta o espaço de endereço e o desempenho, mantendo ainda os aplicativos de 32 bits funcionando perfeitamente. A compatibilidade com 64 bits também melhora o desempenho do OpenSSL quanto a criptografia. Além disso, essa versão introduz novas APIs NDK de mídia nativa, assim como a compatibilidade nativa com OpenGL ES (GLES) 3.1.
Para usar a compatibilidade com 64 bits proporcionada pelo Android 5.0, baixe e instale a revisão 10c do NDK pela página do Android NDK. Consulte as notas da versão da revisão 10c para saber mais sobre as mudanças importantes e correções de erro do NDK.
Vinculação a um serviço
O método Context.bindService()
agora exige uma Intent
explícita e aciona uma exceção se uma intent implícita for fornecida. Para garantir a segurança do aplicativo, sempre use uma intent explícita ao iniciar ou vincular Service
e não declare filtros de intent para o serviço.
WebView
O Android 5.0 muda o comportamento padrão do seu aplicativo.
- Se seu aplicativo trabalha com API de nível 21 ou posterior:
- O sistema bloqueia conteúdo misto e cookies de terceiros por padrão. Para permitir conteúdo misto e cookies de terceiros, use os métodos
setMixedContentMode()
esetAcceptThirdPartyCookies()
, respectivamente. - O sistema agora escolhe partes do documento HTML de forma inteligente para apresentar. Esse novo comportamento padrão ajuda a reduzir a área de ocupação da memória e melhora o desempenho. Se você quiser renderizar todo o documento de uma vez só, desative essa otimização chamando
enableSlowWholeDocumentDraw()
.
- O sistema bloqueia conteúdo misto e cookies de terceiros por padrão. Para permitir conteúdo misto e cookies de terceiros, use os métodos
- Se o aplicativo trabalha com APIs de nível inferior a 21: O sistema permite conteúdo misto e cookies de terceiros, e sempre renderiza todo o documento de uma vez só.
Exigência de exclusividade para permissões personalizadas
Conforme documentado no resumo das Permissões, os aplicativos Android podem definir permissões personalizadas como meio de gerenciar o acesso a componentes de forma exclusiva, sem usar permissões de sistema pré-definidas da plataforma. Os aplicativos definem permissões personalizadas em elementos
<permission>
declarados nos arquivos de manifesto.
Há um pequeno número de cenários em que definir permissões personalizadas é uma abordagem legítima e segura. No entanto, criar permissões personalizadas, às vezes, é desnecessário e pode ainda introduzir risco a um aplicativo, dependendo do nível de proteção atribuído às permissões.
O Android 5.0 contém uma mudança de comportamento que garante que apenas um aplicativo possa definir determinada permissão personalizada, a menos que tenha sido assinado com a mesma chave que outros aplicativos que definem a permissão.
Aplicativos que usam permissões personalizadas duplicadas
Qualquer aplicativo pode definir a permissão personalizada que quiser, assim, pode acontecer de diversos aplicativos definirem a mesma permissão personalizada. Por exemplo, se dois aplicativos oferecem um recurso similar, eles podem derivar do mesmo nome lógico para suas permissões personalizadas. Os aplicativos também podem incorporar bibliotecas públicas ou exemplos de código comuns com que incluem as mesmas definições de permissão personalizada.
No Android 4.4 e em anteriores, os usuários puderam instalar diversos aplicativos assim em um determinado dispositivo, embora o sistema tenha atribuído o nível de proteção especificado pelo primeiro aplicativo instalado.
A partir do Android 5.0, o sistema impõe uma nova restrição de exclusividade em permissões personalizadas para aplicativos assinados com chaves diferentes. Agora, apenas um aplicativo de um dispositivo pode definir determinada permissão personalizada (conforme determinado pelo seu nome), a menos que outro aplicativo que define a permissão esteja assinado com a mesma chave. Se o usuário tentar instalar um aplicativo com uma permissão personalizada duplicada e não estiver assinado com a mesma chave que o aplicativo residente que define a permissão, o sistema bloqueará a instalação.
Considerações para o aplicativo
No Android 5.0 e em posteriores, os aplicativos podem continuar definindo suas próprias permissões personalizadas, como faziam antigamente, e solicitando permissões personalizadas de outros aplicativos pelo mecanismo <uses-permission>
. No entanto, com a nova exigência introduzida no Android 5.0, você deve avaliar possíveis impactos no seu aplicativo cuidadosamente.
Veja alguns pontos a considerar:
- O aplicativo declara algum elemento
<permission>
no manifesto? Se sim, eles são realmente necessários para o funcionamento adequado do aplicativo ou serviço? Ou você poderia usar uma permissão padrão do sistema no lugar deles? - Se há elementos
<permission>
no seu aplicativo, você sabe de onde eles vêm? - Você realmente quer que outros aplicativos solicitem suas permissões personalizadas por meio de
<uses-permission>
? - Você usa código clichê ou exemplo de código que contenha elementos
<permission>
no aplicativo? Esses elementos de permissão são realmente necessários? - Suas permissões personalizadas usam nomes simples ou baseados em termos comuns que outros aplicativos eventualmente compartilhem?
Novas instalações e atualizações
Como mencionado acima, novas instalações e atualizações do seu aplicativo em dispositivos com Android 4.4 ou anterior não são afetadas e não possuem mudança de comportamento. Para novas instalações e atualizações em dispositivos com Android 5.0 ou posterior, o sistema impede a instalação do aplicativo se ele definir uma permissão personalizada já definida pelo aplicativo residente existente.
Instalações existentes com atualização de sistema do Android 5.0
Se o aplicativo usar permissões personalizadas e for amplamente distribuído e instalado, há uma chance de ele ser afetado quando usuários atualizarem seu dispositivo para Android 5.0. Depois da instalação da atualização do sistema, o sistema revalida os aplicativos instalados e faz uma verificação de suas permissões personalizadas. Se seu aplicativo definir uma permissão personalizada já definida por outro aplicativo já validado, e o seu aplicativo não estiver assinado com a mesma chave que o outro aplicativo, o sistema não reinstalará o seu aplicativo.
Recomendações
Em dispositivos com Android 5.0 ou posterior, recomendamos examinar o aplicativo imediatamente, fazer os ajustes necessários e publicar a versão atualizada assim que possível.
- Se estiver usando permissões personalizadas no aplicativo, avalie sua origem e se você realmente precisa delas. Remova todos os elementos
<permission>
do aplicativo, a menos que tenha certeza de que eles são necessários para o funcionamento correto do aplicativo. - Considere substituir as permissões personalizadas por permissões padrão do sistema sempre que possível.
- Se seu aplicativo precisar de permissões personalizadas, renomeie-as para que elas sejam exclusivas do seu aplicativo, como anexando-as ao nome completo do pacote do seu aplicativo.
- Se você tiver um conjunto de aplicativos assinados com chaves diferentes, e eles acessam um componente compartilhado por meio de uma permissão personalizada, certifique-se de que a permissão personalizada seja definida apenas uma vez, no componente compartilhado. Aplicativos que usam componente compartilhado não devem definir a permissão personalizada por si só, mas sim devem solicitar acesso pelo mecanismo
<uses-permission>
. - Se você tiver um conjunto de aplicativos assinados com a mesma chave, cada um deles pode definir a(s) mesma(s) permissão(ões) personalizada(s) como necessárias — o sistema permite que os aplicativos sejam instalados da forma normal.
Mudanças na configuração padrão de TLS/SSL
O Android 5.0 introduz mudanças na configuração padrão de TLS/SSL usada por aplicativos para tráfego em HTTPS e em TLS/SSL:
- Os protocolos TLSv1.2 e TLSv1.1 agora estão ativos,
- Os conjuntos de criptografia AES-GCM (AEAD) agora estão ativos,
- Os conjuntos de criptografia MD5, 3DES, export e ECDH de chave estática agora estão inativos,
- Os conjuntos de criptografia Forward Secrecy (ECDHE e DHE) são preferíveis.
Essas mudanças podem gerar problemas na conectividade HTTPS ou TLS/SSL em um pequeno número de casos, que são listados abaixo.
Observe que o ProviderInstaller de segurança do Google Play Services já oferece essas mudanças para as versões anteriores de plataforma Android (até a 2.3).
O servidor não é compatível com nenhum conjunto de criptografia ativo
Por exemplo, um servidor pode ser compatível somente com conjuntos de criptografia 3DES ou MD5. A solução preferível é aprimorar a configuração do servidor para que ele trabalhe com conjuntos e protocolos de criptografia mais seguros e modernos. O ideal seria ter TLSv1.2 e AES-GCM ativos e os conjuntos de criptografia Forward Secrecy (ECDHE, DHE) ativos e sendo os preferenciais.
Uma alternativa é modificar o aplicativo para usar um SSLSocketFactory personalizado para se comunicar com o servidor. O alocador deve ser desenvolvido para criar instâncias de SSLSocket que tenham alguns dos conjuntos de criptografia exigidas pelo servidor ativo, além de conjuntos de criptografia padrão.
O aplicativo está fazendo suposições erradas sobre conjuntos de criptografia usados para se conectar ao servidor
Por exemplo, alguns aplicativos contêm um X509TrustManager personalizado que para porque espera que o parâmetro authType seja RSA, mas encontra ECDHE_RSA ou DHE_RSA.
O servidor é intolerante a extensões TLSv1.1, TLSv1.2 ou TLS novas
Por exemplo, o handshake de TLS/SSL com um servidor é erroneamente rejeitado ou cessa. A solução recomendada é atualizar o servidor para adequá-lo ao protocolo TLS/SSL. Isso fará o servidor negociar esses protocolos mais recentes com sucesso, ou fornecer TLSv1 ou protocolos antigos e ignorar extensões TLS que ele não entenda. Em alguns casos, desativar TLSv1.1 e TLSv1.2 no servidor pode funcionar como uma medida paliativa até que o software do servidor seja atualizado.
Uma alternativa é modificar o aplicativo para usar um SSLSocketFactory personalizado para se comunicar com o servidor. O alocador deve ser atribuído para criar instâncias de SLLSocket somente com os protocolos ativos com os quais o servidor tenha compatibilidade.
Compatibilidade com perfis gerenciados
Os administradores do dispositivo podem adicionar um perfil gerenciado a um dispositivo. Esse perfil é de posse do administrador, conferindo a ele controle sobre o perfil gerenciado e deixando o perfil pessoal do usuário, e seu espaço de armazenamento, sob controle do próprio usuário. Essa mudança pode afetar o comportamento do seu aplicativo das seguintes formas.
Lidar com intents
Os administradores do dispositivo podem restringir acesso a aplicativos do sistema pelo perfil gerenciado. Nesse caso, se um aplicativo disparar pelo perfil gerenciado uma intent que normalmente seria tratada por esse aplicativo, e não houver manipulador adequado para a intent no perfil gerenciado, a intent causará uma exceção. Por exemplo, o administrador do dispositivo pode impedir que aplicativos do perfil gerenciado acessem o aplicativo de câmera do sistema. Se o seu aplicativo for executado no perfil gerenciado e chamar startActivityForResult()
para MediaStore.ACTION_IMAGE_CAPTURE
, e não houver aplicativo no perfil gerenciado que possa tratar da intent, o resultado será uma ActivityNotFoundException
.
Você pode evitar isso verificando se há pelo menos um manipulador para a intent antes de dispará-la. Para procurar um manipulador válido, chame Intent.resolveActivity()
. Você pode ver um exemplo disto em Tire fotos de forma simples: com o aplicativo de Câmera.
Compartilhar arquivos dentre perfis
Cada perfil tem seu próprio armazenamento de arquivos. Como o URI de um arquivo refere-se a um local específico no armazenamento, isso significa que o URI de um arquivo é válido em um perfil e inválido em outro. Normalmente, isso não é um problema para o aplicativo, que normalmente acessa somente os arquivos que cria. No entanto, se um aplicativo anexa um arquivo a uma intent, não é seguro anexar o URI de um arquivo, já que, em algumas circunstâncias, a intent pode ser tratada no outro perfil. Por exemplo, um administrador de dispositivo pode especificar que os eventos de captura de imagem devem ser tratados pelo aplicativo de câmera no perfil pessoal. Se a intent for disparada por um aplicativo no perfil gerenciado, a câmera precisa ser capaz de gravar a imagem em um local em que os aplicativos do perfil gerenciado possa lê-la.
Por questões de segurança, quando você precisar anexar um arquivo a uma intent que possa passar de um perfil para outro, crie e use um URI de conteúdo para o arquivo. Para saber mais sobre como compartilhar arquivos com URIs de conteúdo, veja Compartilhamento de arquivos. Por exemplo, o administrador do dispositivo pode colocar ACTION_IMAGE_CAPTURE
na lista de permissões para que ela seja tratada pela câmera do perfil pessoal. A EXTRA_OUTPUT
da intent disparada deve conter um URI de conteúdo que especifique onde a foto deve ser armazenada. O aplicativo de câmera pode gravar a imagem no local especificado por esse URI, e o aplicativo que disparou a intent poderia acessar esse arquivo para leitura, mesmo que o aplicativo esteja em outro perfil.
Compatibilidade com widget na tela de bloqueio removida
O Android 5.0 removeu a compatibilidade com widgets na tela de bloqueio, mas ainda permite widgets na tela inicial.