Android 在Kotlin中使用Flowable的多个翻新2请求
为了提高我在科特林的技能,我决定做一个演示项目。 演示项目包括在回收器视图中显示帖子,然后在详细信息活动中显示帖子的详细信息。Android 在Kotlin中使用Flowable的多个翻新2请求,android,kotlin,retrofit2,rx-kotlin,Android,Kotlin,Retrofit2,Rx Kotlin,为了提高我在科特林的技能,我决定做一个演示项目。 演示项目包括在回收器视图中显示帖子,然后在详细信息活动中显示帖子的详细信息。 我在显示来自不同api调用的数据时遇到了困难:用户名、标题、文章正文和文章评论数 我的问题是,我希望执行多个请求,然后获得所需的所有数据,以便在详细信息活动中显示它们。这意味着打电话给我用户名,然后打电话给我帖子的评论数。文章的标题和正文来自主活动中完成的请求,我只是将其与包一起传输到详细活动 Api调用: //返回帖子1的评论 //返回用户2的信息 //用于在主活
我在显示来自不同api调用的数据时遇到了困难:用户名、标题、文章正文和文章评论数 我的问题是,我希望执行多个请求,然后获得所需的所有数据,以便在详细信息活动中显示它们。这意味着打电话给我用户名,然后打电话给我帖子的评论数。文章的标题和正文来自主活动中完成的请求,我只是将其与包一起传输到详细活动 Api调用:
//返回帖子1的评论
//返回用户2的信息
//用于在主活动中显示帖子的调用
http:/jsonplaceholder.typicode.com/posts 我还是Rx的新手,我想使用平面图,但我不知道如何在kotlin的Flowable中使用它
var post = viewModel.getPost()
var userStream: Flowable<User> = postService.getUser(post.userId)
var commentsByPostIdCall: Flowable<List<Comment>> = postService.getCommentsByPostId(post.id)
userStream.subscribeOn(Schedulers.io())
.subscribe(object : Subscriber<User> {
override fun onError(t: Throwable?) {
Log.d(this.toString(), " Read of users failed with the following message: " + t?.message);
}
override fun onNext(user: User) {
userTextView.text = user.name
title.text = post.title
body.text = post.body
}
override fun onComplete() {
}
override fun onSubscribe(s: Subscription?) {
if (s != null) {
s.request(1)
}
}
})
var post=viewModel.getPost()
var userStream:Flowable=postService.getUser(post.userId)
var commentsByPostIdCall:Flowable=postService.getCommentsByPostId(post.id)
userStream.subscribeOn(Schedulers.io())
.subscribe(对象:Subscriber){
覆盖有趣的错误(t:可丢弃?){
Log.d(this.toString(),“读取用户失败,并显示以下消息:”+t?.message);
}
覆盖下一页(用户:用户){
userTextView.text=user.name
title.text=post.title
body.text=post.body
}
覆盖有趣的onComplete(){
}
覆盖订阅的乐趣(s:订阅?){
如果(s!=null){
s、 请求(1)
}
}
})
我已将第二个调用放在方法getNumberComments中:
private fun getNumberComments(commentsByPostIdCall:Flowable):Int{
var listComments=listOf()
var listCommentSize=0
commentsByPostIdCall
.subscribeOn(Schedulers.io())
.subscribe(对象:Subscriber){
覆盖有趣的错误(t:可丢弃?){
Log.d(this.toString(),“读取注释失败,出现以下消息:”+t?.message);
}
覆盖下一页(注释:列表){
listComments=注释
}
覆盖有趣的onComplete(){
打印(“完成!”)
listCommentSize=listComments.size
}
覆盖订阅的乐趣(s:订阅?){
如果(s!=null){
s、 请求(1)
}
}
})
返回列表大小
}
我注意到的另一个想法是,有时流没有到达onComplete,有时流在onNext上仍然被阻塞。不明白为什么
任何帮助都将不胜感激!非常感谢:)这就是我解决问题的方法:
Flowable.zip<User, Comments, Pair<User, Comments>>(
postService.getUser(postId),
postService.getCommentsByPostId(postId),
BiFunction { user, comments -> Pair(user, comments) })
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.bindToLifecycle(this)
.map { (first, second) -> Triple(first, second, ExtraDatasFromSomewhere) }
.subscribe({
Log.d("MainActivity", "OnNext")
}, {
Log.d("MainActivity", "OnError")
}, {
Log.d("MainActivity", "OnComplete")
})
Kotlin有一个非常漂亮的lambda函数语法,因此我鼓励您将它们用于特定的subscribe函数:订阅():
http://reactivex.io/RxJava/javadoc/io/reactivex/Flowable.html#subscribe(io.reactivex.functions.Consumer、%20io.reactivex.functions.Consumer、%20io.reactivex.functions.Action)
同样需要注意的是,我不仅使用了原始的Rxjava2库。我使用了以下LIB:
对于
observeOn(AndroidSchedulers.mainThread())
获取主线程。这是因为您在操作UI时没有指定订阅的线程。这样,您就可以在主线程上处理您的订阅。对于
.bindToLifecycle(this)
如果活动已关闭,但您的改装2调用未完成,则这将确保您不会留下内存泄漏我将如何解决此问题:
Flowable.zip<User, Comments, Pair<User, Comments>>(
postService.getUser(postId),
postService.getCommentsByPostId(postId),
BiFunction { user, comments -> Pair(user, comments) })
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.bindToLifecycle(this)
.map { (first, second) -> Triple(first, second, ExtraDatasFromSomewhere) }
.subscribe({
Log.d("MainActivity", "OnNext")
}, {
Log.d("MainActivity", "OnError")
}, {
Log.d("MainActivity", "OnComplete")
})
Kotlin有一个非常漂亮的lambda函数语法,因此我鼓励您将它们用于特定的subscribe函数:订阅():
http://reactivex.io/RxJava/javadoc/io/reactivex/Flowable.html#subscribe(io.reactivex.functions.Consumer、%20io.reactivex.functions.Consumer、%20io.reactivex.functions.Action)
同样需要注意的是,我不仅使用了原始的Rxjava2库。我使用了以下LIB:
对于
observeOn(AndroidSchedulers.mainThread())
获取主线程。这是因为您在操作UI时没有指定订阅的线程。这样,您就可以在主线程上处理您的订阅。对于
.bindToLifecycle(this)
如果活动已关闭,但您的改装2调用未完成,则这将确保您不会留下内存泄漏我刚刚根据需要调整了Kioba建议的解决方案。我把这个贴在这里,以防对某人有用。
我不知道这是否是一种获取评论数量的优雅方式。我刚刚用List因为我只需要两个数据:user和comment,所以我决定使用Pair而不是Triple
Flowable.zip<User, List<Comment>, Pair<User, List<Comment>>>(
postService.getUser(post.id),
postService.getCommentsByPostId(post.id),
BiFunction { user, comments -> Pair(user, comments) })
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.map { (first, second) -> Pair(first, second) }
.subscribe({
Log.d("MainActivity", "OnNext")
userTextView.text = it.first.name
title.text = post.title
body.text = post.body
number_comments.text = it.second.size.toString()
}, {
Log.d("MainActivity", "OnError")
}, {
Log.d("MainActivity", "OnComplete")
})
Flowable.zip(
postService.getUser(post.id),
postService.getCommentsByPostId(post.id),
双功能{user,comments->Pair(user,comments)})
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.map{(第一,第二)->对(第一,第二)}
.订阅({
Log.d(“main活动”、“OnNext”)
userTextView.text=it.first.name
Flowable.zip<User, List<Comment>, Pair<User, List<Comment>>>(
postService.getUser(post.id),
postService.getCommentsByPostId(post.id),
BiFunction { user, comments -> Pair(user, comments) })
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.map { (first, second) -> Pair(first, second) }
.subscribe({
Log.d("MainActivity", "OnNext")
userTextView.text = it.first.name
title.text = post.title
body.text = post.body
number_comments.text = it.second.size.toString()
}, {
Log.d("MainActivity", "OnError")
}, {
Log.d("MainActivity", "OnComplete")
})