我希望能够在我的ViewModel中使用Kotlin协程在Firebase DB中收听实时更新。
问题是,无论何时在集合中创建新消息,我的应用程序都会冻结,并且不会从此状态恢复。我需要杀死它并重新启动应用程序。
它第一次通过,我可以在UI上看到以前的消息。第二次调用SnapshotListener
时会发生此问题。
我的observer()
功能
val channel = Channel<List<MessageEntity>>()
firestore.collection(path).addSnapshotListener { data, error ->
if (error != null) {
channel.close(error)
} else {
if (data != null) {
val messages = data.toObjects(MessageEntity::class.java)
//till this point it gets executed^^^^
channel.sendBlocking(messages)
} else {
channel.close(CancellationException("No data received"))
}
}
}
return channel
这就是我想要观察消息的方式
launch(Dispatchers.IO) {
val newMessages =
messageRepository
.observer()
.receive()
}
}
在用sendBlocking()
替换send()
后,我仍然没有在频道中收到任何新消息。 SnapshotListener
方面被执行
//channel.sendBlocking(messages) was replaced by code bellow
scope.launch(Dispatchers.IO) {
channel.send(messages)
}
//scope is my viewModel
如何使用Kotlin协同程序观察firestore / realtime-dbs中的消息?
我最终得到的是我使用Flow,它是coroutines 1.2.0-alpha-2
的一部分
return flowViaChannel { channel ->
firestore.collection(path).addSnapshotListener { data, error ->
if (error != null) {
channel.close(error)
} else {
if (data != null) {
val messages = data.toObjects(MessageEntity::class.java)
channel.sendBlocking(messages)
} else {
channel.close(CancellationException("No data received"))
}
}
}
channel.invokeOnClose {
it?.printStackTrace()
}
}
这就是我在ViewModel中观察它的方式
launch {
messageRepository.observe().collect {
//process
}
}
更多关于主题https://medium.com/@elizarov/cold-flows-hot-channels-d74769805f9