【发布时间】:2021-06-29 15:10:09
【问题描述】:
所以我正在关注 MVI 架构以及如何处理多个 api 调用结果,所以我的代码如下所示,我使用 https://github.com/RohitSurwase/AAC-MVI-Architecture 作为参考
Modal.kt
data class HomeViewState(val postListState: PostListState)
sealed class PostListState {
object Loading : PostListState()
data class Success(val postList: List<Post>) : PostListState()
data class Error(val message: String) : PostListState()
}
ViewModal.kt
private fun fetchPostFeed() {
composite.add(postUseCase.fetchPostList().subscribe(
{ postList ->
viewState = viewState.copy(postListState = PostListState.Success(postList))
},
{ error ->
viewState = viewState.copy(
postListState = PostListState.Error(
message = error.localizedMessage ?: "Something went wrong while fetching postlist!!!"
)
)
Timber.e(error)
}
))
}
Fragment.kt
override fun renderViewState(viewState: HomeViewState) {
when (viewState.postListState) {
PostListState.Loading -> loadPosts()
is PostListState.Success -> showPostListToUI(viewState.postListState.postList)
is PostListState.Error -> showErrorLayout(viewState.postListState.message)
}
}
所以流程是当 ViewModel 初始化默认状态设置为 PostListState.Loading 时,这个状态改变片段的 renderViewState() 被调用并发出加载事件,即由 fetchPostFeed() 中的视图模型处理,在成功或错误的情况下会再次更新状态。
问题
现在我还想调用 API 来加载 cmets,所以我尝试将实现更改为类似
Modal.kt
data class HomeViewState(val postListState: PostListState, val commentsState: CommentsState)
sealed class PostListState {
object Loading : PostListState()
data class Success(val postList: PagedList<Post>) : PostListState()
data class Error(val message: String) : PostListState()
}
sealed class CommentsState {
object Loading : CommentsState()
data class Success(val commList: List<Comments>) : CommentsState()
data class Error(val message: String) : CommentsState()
}
我们将在片段中
Fragment.kt
override fun renderViewState(viewState: HomeViewState) {
when (viewState.postListState) {
PostListState.Loading -> loadPosts()
is PostListState.Success -> showPostListToUI(viewState.postListState.postList)
is PostListState.Error -> showErrorLayout(viewState.postListState.message)
}
when (viewState.commentsState) {
CommentsState.Loading -> loadComments()
is CommentsState.Success -> showCOmments(viewState.commentsState.commList)
is CommentsState.Error -> showErrorLayout(viewState.commentsState.message)
}
}
现在的事情是假设 post fetch 较早完成并且状态更新为 PostListState.Success 并且如果评论状态仍处于 CommentsState.Loading 它将重新触发加载 cmets,这是不希望的。 如何处理多个 api 调用,以便更改一个 API 调用的状态不会重新触发其他 api 调用中的事件
【问题讨论】: