DEV Community

Cover image for Utilizando o Jetpack Paging v3
João Gabriel
João Gabriel

Posted on

3 2

Utilizando o Jetpack Paging v3

O que é a Paging Library?

A Paging Library, é uma biblioteca criada pelo Google para resolver o problema da paginação de dados no Android.

Um problema que geralmente temos que resolver ao criar um aplicativo, é a solicitação de dados longos, que não exigem uma única vez, pois o usuário vê apenas uma pequena parte desses dados por vez.

Uma maneira de resolver esse problema, é adicionar um ScrollListener para o RecyclerView e carregar mais dados quando o usuário chega ao final da lista. Com esta abordagem, é difícil manter a eficiência, também a lógica da interface do usuário e gera uma lógica de dados complicada, o que dificulta a depuração e testes do projeto.

Vantagens

  • A Paging Library ajuda a carregar e exibir pequenos blocos de dados por vez.

  • O carregamento de dados parciais sob demanda reduz o uso da largura de banda da rede e dos recursos do sistema.

  • Facilmente integrada ao RecyclerView.

  • Mantém o controle das chaves a serem usadas para recuperar a página seguinte e a anterior.

  • Solicita automaticamente a página correta quando o usuário rola para o final da lista.

  • Garante que várias solicitações não sejam acionadas ao mesmo tempo.

  • Rastreia o estado de carregamento e permite exibi-lo em um RecyclerView item da lista, ou em qualquer outro local da interface do usuário e mostrar facilmente as cargas com falha.

Novidades Paging 3

  • Suporte interno para tratamento de erros, incluindo mecanismo de reload e retry.
  • Suporte à coroutines e Flow do Kotlin, assim como era ao LiveData e RxJava na versão 2.
  • Header, footer e separator incluídos na biblioteca.

Como implementar

Primeiramente, é necessário ter o Android Studio na versão 3.6 ou superior.

Adicionar a dependência no build.gradle

def paging_version = "3.0.0-alpha02"
implementation "androidx.paging: paging-runtime: $ paging_version"
Enter fullscreen mode Exit fullscreen mode

Até o momento da escrita deste artigo, esta é a versão atual da biblioteca

Fluxo dos dados

Alt Text

O principal componente na camada de Repository é o PagingSource.
Cada objeto PagingSource, define uma fonte de dados e recupera os dados dessa fonte, seja ela um banco de dados local ou uma API externa. No nosso exemplo utilizarei uma API externa:

class MyPagingSource(
    private val api: MyApi
) : PagingSource<Int, MyModel>() {
    override suspend fun load(params: LoadParams<Int>): LoadResult<Int, MyModel> {
        return try {
            val result = api.getItems(params.key ?: STARTING_PAGE_INDEX)
            Page(
                data = result,
                prevKey = params.key,
                nextKey = result.nextPage ?: STARTING_PAGE_INDEX.plus(1)
            )
        } catch (e: IOException) {
            LoadResult.Error(e)
        } catch (e: HttpException) {
            LoadResult.Error(e)
        }
    }

    companion object {
        private const val STARTING_PAGE_INDEX = 1
    }
}
Enter fullscreen mode Exit fullscreen mode

A partir da criação do nosso PagingSource na camada de Repository, criaremos o nosso Pager.

O Pager é o responsável por configurar o tamanho de nossas páginas de requisição, através do PagingConfig, e auxiliar no fluxo dos dados.

fun getItems(): Flow<PagingData<MyModel>> {
    return Pager(
          config = PagingConfig(pageSize = 20),
          pagingSourceFactory = { MyPagingSource(api = api) }
    ).flow.cachedIn(viewModelScope)
}
Enter fullscreen mode Exit fullscreen mode

A partir da Paging v3, não é necessário converter Flow em LiveData.
Para manter um cache dos dados carregados no nosso ViewModel, chamamos o cachedIn passando o nosso androidx.lifecycle.viewModelScope

Agora teremos a nossa última etapa de implementação, que é passar os dados carregados para a nossa View.

Será necessário coletar os dados vindos do PagingData e passar para o nosso Adapter:

  • Solicitando os dados para o viewModel:
fun getData() {
    lifecycleScope.launch {
        viewModel.getItems().collectLatest {
            adapter.submitData(it)
        }
     }
}
Enter fullscreen mode Exit fullscreen mode
  • A implementação do adapter só precisa fazer uma extensão da classe PagingDataAdapter, e passar um DiffUtilCallback para diferenciar os itens recebidos:
class MyAdapter : PagingDataAdapter<MyModel, MyAdapter.MyViewHolder>(DiffUtilCallback()) {
   // a implementação do corpo do adapter permanece a mesma
}

class DiffUtilCallBack : DiffUtil.ItemCallback<MyModel>() {
    override fun areItemsTheSame(oldItem: MyModel, newItem: MyModel): Boolean {
        return oldItem.id == newItem.id
    }

    override fun areContentsTheSame(oldItem: MyModel, newItem: MyModel): Boolean {
        return oldItem == newItem
    }
}
Enter fullscreen mode Exit fullscreen mode

Esta foi a implementação necessária para fazer paginação no Android usando a Paging Library, obrigado pela leitura

Todo o conteúdo foi compartilhado no meu Github

Vou deixar aqui links adicionais com a documentação da biblioteca:

https://developer.android.com/topic/libraries/architecture/paging/v3-overview

https://codelabs.developers.google.com/codelabs/android-paging/#0

AWS Security LIVE!

Join us for AWS Security LIVE!

Discover the future of cloud security. Tune in live for trends, tips, and solutions from AWS and AWS Partners.

Learn More

Top comments (0)

Heroku

This site is built on Heroku

Join the ranks of developers at Salesforce, Airbase, DEV, and more who deploy their mission critical applications on Heroku. Sign up today and launch your first app!

Get Started