ExN*_*ura 4 android kotlin android-viewmodel kotlin-coroutines kotlin-flow
所以我有一个 ViewModel 我正在尝试进行单元测试。它使用 stateIn 运算符。我找到了有关如何测试使用 stateIn 运算符创建的状态流的文档https://developer.android.com/kotlin/flow/test但即使我正在收集流,mapLatest也永远不会触发。
\nclass DeviceConfigurationViewModel(\n val systemDetails: SystemDetails,\n val step: AddDeviceStep.ConfigureDeviceStep,\n val service: DeviceRemoteService\n) : ViewModel(), DeviceConfigurationModel {\n\n @OptIn(ExperimentalCoroutinesApi::class)\n private val _state: StateFlow<DeviceConfigurationModel.State> =\n service.state\n .mapLatest { state ->\n when (state) {\n DeviceRemoteService.State.Connecting -> {\n DeviceConfigurationModel.State.Connecting\n }\n is DeviceRemoteService.State.ConnectedState.Connected -> {\n state.sendCommand(step.toCommand(systemDetails))\n DeviceConfigurationModel.State.Connected\n }\n is DeviceRemoteService.State.ConnectedState.CommandSent -> {\n DeviceConfigurationModel.State.Configuring\n }\n is DeviceRemoteService.State.ConnectedState.MessageReceived -> {\n transformMessage(state)\n }\n is DeviceRemoteService.State.Disconnected -> {\n transformDisconnected(state)\n }\n }\n }\n .distinctUntilChanged()\n .stateIn(\n viewModelScope,\n SharingStarted.WhileSubscribed(5000), // Keep it alive for a bit if the app is backgrounded\n DeviceConfigurationModel.State.Disconnected\n )\n\n override val state: StateFlow<DeviceConfigurationModel.State>\n get() = _state\n\n private fun transformDisconnected(\n state: DeviceRemoteService.State.Disconnected\n ): DeviceConfigurationModel.State {\n return if (state.hasCause) {\n DeviceConfigurationModel.State.UnableToConnect(state)\n } else {\n state.connect()\n DeviceConfigurationModel.State.Connecting\n }\n }\n\n private fun transformMessage(state: DeviceRemoteService.State.ConnectedState.MessageReceived): DeviceConfigurationModel.State {\n return when (val message = state.message) {\n is Message.AddedToProject -> DeviceConfigurationModel.State.Configured\n is Message.ConfigWifiMessage -> {\n if (!message.values.success) {\n DeviceConfigurationModel.State.Error(\n message.values.errorCode,\n state,\n step.toCommand(systemDetails)\n )\n } else {\n DeviceConfigurationModel.State.Configuring\n }\n }\n }\n }\n\n}\n
Run Code Online (Sandbox Code Playgroud)\n这是我的单元测试。即使我正在收集流量,mapLatest 似乎也永远不会被触发。我正在使用此处的建议https://developer.android.com/kotlin/flow/test
\n@OptIn(ExperimentalCoroutinesApi::class)\nclass DeviceConfigurationViewModelTest {\n\n private val disconnectedService = mock<DisconnectedService>()\n\n private val deviceServiceState: MutableStateFlow<DeviceRemoteService.State> =\n MutableStateFlow(DeviceRemoteService.State.Disconnected(disconnectedService, Exception()))\n\n private val deviceService = mock<DeviceRemoteService> {\n on { state } doReturn deviceServiceState\n }\n\n private val systemDetails = mock<SystemDetails> {\n\n on { controllerAddress } doReturn "192.168.1.112"\n\n on { controllerName } doReturn "000FFF962FE7"\n\n }\n\n private val step = AddDeviceDeviceStep.ConfigureDeviceStep(\n 44,\n "Thou Shalt Not Covet Thy Neighbor\xe2\x80\x99s Wifi",\n "testing616"\n )\n\n private lateinit var viewModel: DeviceConfigurationViewModel\n\n @Before\n fun setup() {\n viewModel = DeviceConfigurationViewModel(systemDetails, step, deviceService)\n }\n\n @Test\n fun testDeviceServiceDisconnectWithCauseMapsToUnableToConnect() =\n runTest {\n\n val collectJob = launch(UnconfinedTestDispatcher()) { viewModel.state.collect() }\n\n deviceServiceState.emit(\n DeviceRemoteService.State.Disconnected(Exception("Something bad happened"))\n )\n\n assertThat(viewModel.state.value).isInstanceOf(DeviceConfigurationModel.State.UnableToConnect::class.java)\n collectJob.cancel()\n }\n\n}\n
Run Code Online (Sandbox Code Playgroud)\n
归档时间: |
|
查看次数: |
1798 次 |
最近记录: |