Since you have 'refresh' scenario and using Room db, I am guessing you are using Paging3 with network+local db pattern(with Room db as local cache).
I had a similar situation with network + local db pattern. I am not sure if I understand your question correctly, or your situation is the same as the one I had, but I'll share what I did anyway.
What I was using:
- Paging3: 3.0.0-beta01
- Room: 2.3.0-beta02
What I did was let Room library to create PagingSource (with the key of Int
), and let RemoteMediator handle all the other cases, such as fetching the data from network when refreshing and/or appending, and inserting them into db right after fetch success.
My dao
function for creating PagingSource from Room Library:
@Query("SELECT * FROM article WHERE isUnread = 1")
fun getUnreadPagingSource(): PagingSource<Int, LocalArticle>
In my case I defined Repository class to have dao
class in its constructor to call the function above from repository when creating Pager class.
My custom RemoteMediator class looks something like this below:
- Note: In my case, there is no PREPEND case so
RemoteMediator#load
function always returns true
when the value of the argument loadType
is LoadType.PREPEND
.
class FeedMediator(
private val repository: FeedRepository
) : RemoteMediator<Int, LocalArticle>() {
...
override suspend fun load(
loadType: LoadType,
state: PagingState<Int, LocalArticle>
): MediatorResult = runCatching {
when (loadType) {
LoadType.PREPEND -> true
LoadType.REFRESH -> {
feedRepository.refresh()
false
}
LoadType.APPEND -> {
val continuation = feedRepository.continuation()
if (continuation.isNullOrEmpty()) {
true
} else {
loadFeedAndCheckContinuation(continuation)
}
}
}
}.fold(
onSuccess = { endOfPaginationReached -> MediatorResult.Success(endOfPaginationReached) },
onFailure = {
Timber.e(it)
MediatorResult.Error(it)
}
)
private suspend fun loadFeedAndCheckContinuation(continuation: String?): Boolean {
val feed = feedRepository.load(continuation)
feedRepository.insert(feed)
return feed.continuation.isNullOrEmpty()
}
Finally you can create Pager
class.
fun createFeedPager(
mediator: FeedMediator<Int, LocalArticle>,
repository: FeedRepository
) = Pager(
config = PagingConfig(
pageSize = FETCH_FEED_COUNT,
enablePlaceholders = false,
prefetchDistance = PREFETCH_DISTANCE
),
remoteMediator = mediator,
pagingSourceFactory = { repository.getUnreadPagingSource() }
)
I hope it helps in some way..
Other references:
EDIT:
After reading the doc again, I found a statement where the doc clearly states:
RemoteMediator to use for loading the data from the network into the local database.