Home > Blockchain >  Why sharedFlow collect won't execute this line?
Why sharedFlow collect won't execute this line?

Time:06-15

I define a sharedFlow in MainViewModel like

class MainViewModel : ViewModel{
    val _sharedFlow: MutableSharedFlow()
    val sharedFlow = _sharedFlow.asSharedFlow()
}

Then I have a activity

lifecycleScope.launch { 
    repeatOnLifecycle(Lifecycle.State.STARTED){
        viewModel.sharedFlow.collect{
            Log.i("View","Here can be call.")
        }
        Log.i("View","this line will never call.")
    }
}

when I click a button to emit , collect will be called , then when I rotate this or back to previous activity , when this activity destroy it should be leave"collect" block then execute

Log.i("View","this line will never call")

right? but it doesn't ,does anyone knows why ? thanks

CodePudding user response:

SharedFlow is a hot stream of data, which is collected infinitely until subscriber is cancelled. This usually happens when the scope in which the coroutine is running is cancelled. When Activity is destroyed, the corresponding lifecycleScope and all launched coroutine are cancelled, item collection and emission are also cancelled. When coroutine is canceled it doesn't mean that the code after collect will be executed, but wise versa - the code after collect will not be executed due to cancellation of the coroutine.

So basically the line

Log.i("View","this line will never call")

will never be executed unless the collected Flow is cold(finite).

You can launch a separate coroutine to collect the flow, then the line, which prints the log, will be executed:

lifecycleScope.launch {
    repeatOnLifecycle(Lifecycle.State.STARTED) {
        launch {
            viewModel.sharedFlow.collect{
                Log.i("View","Here can be call.")
            }
        }
        Log.i("View","this line will never call.")
    }
}
  • Related