Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/187.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android 如何使用分页3处理许多Api请求_Android_Kotlin_Android Paging - Fatal编程技术网

Android 如何使用分页3处理许多Api请求

Android 如何使用分页3处理许多Api请求,android,kotlin,android-paging,Android,Kotlin,Android Paging,接下来,我使用RemoteMediator实现了分页和缓存(我调用了一个简单的API,返回一个新闻列表)。我将这个RemoteMediator注入到存储库中,该存储库具有返回Flow的方法getResultStream()。在ViewModel中是函数getNews():Flow,在片段中我调用这个函数并将列表提交给RecyclerAdapter 现在我想添加一个新的API调用,它返回新闻,但带有搜索关键字。正确的方法是什么?我是否必须重新编写所有这些代码并创建一个新的RemoteMediato

接下来,我使用
RemoteMediator
实现了分页和缓存(我调用了一个简单的API,返回一个新闻列表)。我将这个
RemoteMediator
注入到存储库中,该存储库具有返回
Flow
的方法
getResultStream()
。在ViewModel中是函数
getNews():Flow
,在片段中我调用这个函数并将列表提交给RecyclerAdapter

现在我想添加一个新的API调用,它返回新闻,但带有搜索关键字。正确的方法是什么?我是否必须重新编写所有这些代码并创建一个新的
RemoteMediator
?逻辑将是相同的,但现在我必须将一个字符串参数传递给改型get函数。此调用的结果将替换RecyclerView中的项,因此我将有两个数据源,但只有一个回收器,我是否还必须创建一个
中介LiveData
?(我不添加任何代码,但如果有帮助,我可以添加)


一个人问我到底是怎么做的(这个问题作为答案贴出来的,所以现在被删除了,但也许将来会对别人有所帮助)。因此,在ViewModel中,我有:

//此流保留查询。若为空,则表示我希望从API获取所有新闻。如果它不为null,则意味着我要发出另一个接受参数查询的API请求
private val_queryFlow:MutableStateFlow=MutableStateFlow(null)
val queryFlow:StateFlow
get()=\u queryFlow
//此函数用于设置和验证查询
有趣的submitQuery(查询:字符串?)
{
Timber.d(“提交新的搜索$query”)
_queryFlow.value=when
{
query.isNullOrEmpty()->null
query.trim()
.isNotBlank()->query.trim()
else->null
}
}
//我在RecyclerView中使用的分页数据流
@实验常规
val homeNewsData=\u queryFlow.flatMapLatest{
搜索新闻(it)
}
私人娱乐搜索新闻(
查询:字符串?
):流动
{
return newsRepository.getSearchResultStream(
查询
)
//映射、过滤、分离器等。
.cachedIn(viewModelScope)
}
NewsRepository在VM中使用了以下功能:

fun getSearchResultStream(searchKey:String?):流
{
val pagingSourceFactory={database.cacheNewsDao.getNews()}
传呼机(
config=PagingConfig(
pageSize=网络页面大小,
enablePlaceholders=false,
initialLoadSize=初始加载大小
),
remoteMediator=newsRemoteMediator.apply{this.searchKey=searchKey},
pagingSourceFactory=pagingSourceFactory
).流动
}
NewsRemoteMedietor:

//它保存提交的查询。基于此,我可以定义我要执行的API请求
var searchKey:字符串?=无效的
覆盖挂起乐趣加载(加载类型:加载类型,状态:PagingState):结果
{
\\所有的逻辑都和codelabs一样
尝试
{
val-Api反应=
if(searchKey.isNullOrEmpty())//查询为null/empty获取趋势新闻
NewsReformation.getTrending(
state.config.pageSize,
page*state.config.pageSize
)
否则//查询不为空,使用搜索关键字发出API请求
NewsReformation.getSearched(
state.config.pageSize,
页面*state.config.pageSize,
搜索键!!
)
\\同样的逻辑,就像codelabs一样
}
}
我不知道这是否是最好的方法(可能不是),但在我的情况下,它是有效的
假设您还有一个recyclerview,您可以执行以下操作:

val queryFlow = MutableStateFlow(startingQuery)
queryFlow.flatMapLatest { query ->
    Pager(..., MyRemoteMediator(query)) {
        MyPagingSource(...)
    }.flow
}