https://kotlinlang.org logo
Title
p

Pablo

12/20/2021, 11:40 AM
Is is possible detect when the scope is canceled in a flow
.onCompletion
? I have this flow :
flow {
  for(foo in bar downTo 0){
    emit(foo)
    delay(1_000L)
  }
}
Then I consume it :
myFlow()
 .onEach {
    updateUI
  }
 .onCompletion {
   //Do something but only when the timer is 0 not when cancelled
 }
 .launchIn(scope)

In some point I do cancel the scope and it automatically get into `onCompletion` so even if the timer is not over yet, it does the thing of timer finished because I have the code there, is there any way I can get if the completion is because ok the for loop or for a cancellation of scope?
s

stojan

12/20/2021, 12:17 PM
in
onCompletion
you have access to the Throwable (if canceled) or null otherwise:
flow.onCompletion { if (it == null) println("Completed successfully") }
1
p

Pablo

12/20/2021, 12:32 PM
I've also tried
if(currentCoroutineContext().isActive) completed
But is there any generic way so I don't update every
onCompletion{}
of my project?
p

Paul Woitaschek

12/20/2021, 12:32 PM
Write an extension function
Sth like:
public fun <T> Flow<T>.onCompletionIfNotCancelled(
  action: suspend FlowCollector<T>.() -> Unit
): Flow<T> {
  return onCompletion {
    if (it !is CancellationException) {
      action()
    }
  }
}
1