android - 这些参数与注入的调度程序有什么不同?
问题描述
这两种方法调用相同的用例。在第一个版本中,我对 进行了硬编码Dispatchers.IO
,并且事情按预期工作。
第二个版本(我更喜欢)使用默认Dispatchers.IO
类型的注入调度程序。它因注释中描述的 IllegalStateException 而失败。有任何想法吗?
@HiltViewModel
class MainViewModel @Inject constructor(
private val getUsers: GetUsers,
private val dispatcher: CoroutineDispatcher = Dispatchers.IO,
) : ViewModel() {
val liveData: MutableLiveData<List<User>> = MutableLiveData()
suspend fun getUsersByParamDispatcher(params: GetUsers.Params) {
// Successfully works as intended.
viewModelScope.launch(Dispatchers.IO) {
getUsers(params).collectLatest {
liveData.postValue(it)
}
}
}
suspend fun getUsersByInjectDispatcher(params: GetUsers.Params) {
// IllegalStateException: Cannot access database on the main thread since it may potentially
// lock the UI for a long period of time.
// at androidx.room.RoomDatabase.assertNotMainThread(RoomDatabase.java:494).
viewModelScope.launch(dispatcher) {
getUsers(params).collectLatest {
liveData.postValue(it)
}
}
}
}
日志确认了异常,我的好奇心是它们为什么不同,以及我将如何获得有效的注入版本。
注入 Dispatchers.IO 失败:
>> coroutine.name: main
工作参数 Dispatchers.IO:
>> coroutine.name: DefaultDispatcher-worker-1
依赖项由提供@HiltViewModel
,我希望调度程序尊重其分配的默认值。by viewModels()
Fragment 使用委托创建此视图模型。
对调度程序进行硬编码可能很好。但是通过注入,TestCoroutineDispatcher
在测试期间很容易通过阻塞。
也许我忽略了一些简单的东西,或者完全是另一种方式。
// MainViewModelTest
@Before
fun setup() {
MockKAnnotations.init(this)
viewModel = MainViewModel(
getUsers,
coroutinesTestRule.testDispatcher
)
}
解决方案
推荐阅读
- sas - 带有 BY 语句错误消息的逻辑回归
- matlab - MATLAB 文档中给出的关于 montage 函数返回错误的代码
- java - 未记录 Axis/Log4J 致命消息
- java - 为什么书上说 JDBC 破坏了 Parental 委托模型?
- javascript - 使用子组件生成动态数据字段
- python - 设置 Flask DB2 连接
- git - SVN 到 Git 迁移,其中 SVN 存储库中有存储库
- javascript - 如果用户单击浏览器后退按钮,如何将用户重定向到页面?
- haskell - Haskell - 无法匹配预期类型
- ms-access - 访问表单的动态组合框问题