Kotlin Coroutines viewModelScope 中的改造调用

Retrofit call in Kotlin Coroutines viewModelScope

最近我更新了我的 ViewModel 以使用新的 viewModelScope。从它的实现中,我看到 Dispatchers.Main.immediate 被设置为 viewModelScope 的默认值 CoroutineDispatcher

因此,当在 viewModelScope.launch 中打印当前 Thread 时,它会给出 Thread[main,5,main]

但这是我的问题。虽然这在主线程中运行,但以下代码对我有用,它执行网络调用。

viewModelScope.launch {
    userRepo.login(email, password)
}

这里userRepo.login(email, password)suspend函数,调用了Retrofitsuspend函数

如果我的当前线程是主线程,那么这是如何工作的?

之所以有效,是因为 Retrofit 的 suspend 实现委托给了 Call<T>.enqueue。这意味着默认情况下它已经在自己的后台执行程序上执行,而不是使用调用者的 Dispatcher.

从主线程调用挂起函数总是安全的。但是,如果您要执行繁重的操作,例如从服务器、数据库、内容加载器获取数据……最好使用适当的调度程序,例如 Dispatcher.IO。

如果您愿意,可以将此调度程序与 viewmodelScope 一起使用,然后所有挂起函数都将与此调度程序一起运行。

现在 ViewModel 是一个执行器(一个 class 将执行从 Main 更改为后台)

如果您要更改 ViewModel 中的调度程序,一个好的做法是通过构造函数注入此 Dispatcher 以测试 ViewModel。