【发布时间】:2021-05-31 11:10:48
【问题描述】:
我正在编写我的第一个 Kotlin 应用程序,并且正在使用 firebase 服务进行身份验证、数据库和存储。由于无法进行原子 Firestore + Storage 操作,我发现自己正在退出回调地狱以进行简单的图像上传(带有错误回退和所有)。因此 - 我决定重构我的应用程序以使用协程。我找到了一些示例(例如here 和here),但我注意到这些示例中的存储库级函数没有像android docs 中所示的withContext(Dispatchers.IO){ } 包装。他们应该吗?我猜这是两个问题合二为一:
- 是否应始终使用 IO 调度程序调用 Firebase 操作?
-
kotlinx-coroutines-play-services的Task<T>.await()主安全吗?
还有一个额外的问题:我将所有 Firebase 调用包装在一个代理对象中以进行解耦 - 有没有办法将对象(/类)的所有函数设置为在相同的上下文中运行,或者我必须包装每个分别与withContext(Dispatchers.IO){ } 一起工作?
非常感谢!
【问题讨论】:
-
按照惯例,所有挂起函数都是主安全的。可以组合一个不是的,但如果这些 await() 函数不是,那将是库作者的错误。
withContext用于调用非挂起阻塞函数。 -
所以我想说,按照相同的约定,我必须将所有函数编写为 main-safe 作为一个好习惯,对吧?这样做的方法是用
withContext(Dispatchers.xxx)包装每个函数,还是我误解了它的用法? -
在协程和挂起函数中使用
withContext来调用阻塞函数(不立即返回且不是挂起函数的函数),或者调用需要在主线程上调用的函数您目前不在主要调度员上。按照惯例,挂起函数永远不会阻塞。 -
您的挂起功能绝对应该是主要安全的。如果您完全致力于使用协程,那么是的,您可能会将自己代码中的任何阻塞函数转换为非阻塞挂起函数,因此它们将是主安全的。
-
我想我现在将我所有的存储库函数都转换为挂起函数。有没有办法为对象的所有函数设置上下文?
标签: android firebase kotlin kotlin-coroutines