Evitar downloads não otimizados

Alguns dos usuários do seu app têm acesso intermitente à Internet ou têm limites com base na quantidade de informações que podem baixar nos dispositivos deles. Você pode incentivar os usuários a interagir com seu aplicativo com mais frequência reduzindo a quantidade de dados que seu app precisa transferir por download.

A maneira mais básica de reduzir seus downloads é fazer download apenas do que você precisam. Em termos de dados, isso significa implementar APIs REST que permitem especificar critérios de consulta que limitam os dados retornados usando parâmetros como quando foi feita a última atualização.

Da mesma forma, ao fazer o download de imagens, é recomendado reduzir o tamanho do lado do servidor, em vez de baixar imagens em tamanho original que são reduzidas no cliente.

Armazenar respostas HTTP em cache

Outra técnica importante é evitar o download de dados duplicados. Você pode reduzir a probabilidade de fazer o download do mesmo dado repetidamente usando armazenamento em cache. Ao armazenar em cache os dados e recursos de seu aplicativo, você cria uma cópia local dos as informações que o app precisa referenciar. Caso seu app precise acessar a mesma informação várias vezes em um curto período, você precisa para baixá-lo no cache apenas uma vez.

É importante armazenar em cache o mais agressivamente possível para reduzir o total de dados que você transfere por download. Sempre armazene em cache recursos estáticos, incluindo downloads sob demanda, como imagens em tamanho original, pelo tempo razoável sempre que possível. Os recursos sob demanda devem ser armazenados separadamente para que você possa limpar regularmente seu cache sob demanda para gerenciar o tamanho dele.

Para garantir que o armazenamento em cache não faça seu app mostrar dados desatualizados, use os códigos de status HTTP e cabeçalhos, como o ETag e Last-Modified e cabeçalhos de cache válidos. Isso permite que você determine quando o conteúdo associado deve ser atualizado. Exemplo:

Kotlin

// url represents the website containing the content to place into the cache.
val conn: HttpsURLConnection = url.openConnection() as HttpsURLConnection
val currentTime: Long = System.currentTimeMillis()
val lastModified: Long = conn.getHeaderFieldDate("Last-Modified", currentTime)

// lastUpdateTime represents when the cache was last updated.
if (lastModified < lastUpdateTime) {
    // Skip update
} else {
    // Parse update
    lastUpdateTime = lastModified
}

Java

// url represents the website containing the content to place into the cache.
HttpsURLConnection conn = (HttpsURLConnection) url.openConnection();
long currentTime = System.currentTimeMillis();
long lastModified = conn.getHeaderFieldDate("Last-Modified", currentTime);

// lastUpdateTime represents when the cache was last updated.
if (lastModified < lastUpdateTime) {
    // Skip update
} else {
    // Parse update
    lastUpdateTime = lastModified;
}

Você pode configurar algumas bibliotecas de rede para respeitar esses códigos de status e automaticamente os cabeçalhos. Ao usar OkHttp, por exemplo, configurar um diretório de cache e um tamanho de cache para o cliente permitirão que a biblioteca use Armazenamento em cache HTTP, conforme mostrado no exemplo de código a seguir:

Kotlin

val cacheDir = Context.getCacheDir()
val cacheSize = 10L * 1024L * 1024L // 10 MiB
val client: OkHttpClient = OkHttpClient.Builder()
    .cache(Cache(cacheDir, cacheSize))
    .build()

Java

File cacheDir = Context.getCacheDir();
long cacheSize = 10L * 1024L * 1024L; // 10 MiB
OkHttpClient client = new OkHttpClient.Builder()
    .cache(new Cache(cacheDir, cacheSize))
    .build();

Com o cache configurado, é possível exibir solicitações HTTP totalmente armazenadas em cache diretamente do armazenamento local, eliminando a necessidade de abrir uma conexão de rede. As respostas armazenadas em cache condicionalmente podem validar sua atualização no servidor, eliminando o custo da largura de banda associada ao download. Respostas sem cache são armazenados no cache de resposta para solicitações futuras.

Para armazenar dados não confidenciais em um diretório de cache externo não gerenciado, usando Context.getExternalCacheDir() Como alternativa, você pode armazenar dados em cache no cache de aplicativos gerenciados e seguros usando Context.getCacheDir() Esse cache interno poderá ser liberado quando o sistema estiver com pouco armazenamento disponível.

Usar um repositório

Para uma abordagem mais sofisticada de armazenamento em cache, considere o design do repositório padrão Isso envolve a criação de uma classe personalizada, conhecida como repositório, que fornece uma abstração de API sobre alguns dados ou recursos específicos. O repositório pode, inicialmente, buscar seus dados de várias fontes, como um serviço da Web remoto, mas fornece aos autores da chamada uma versão em cache dos dados em chamadas subsequentes. Isso de indireção permite fornecer uma estratégia robusta de armazenamento em cache que é específicas para seu app. Para mais informações sobre como usar o padrão Repository em seu aplicativo, consulte o Guia para aplicativo do Terraform.