https://kotlinlang.org logo
#coroutines
Title
# coroutines
l

lukaswelte

10/12/2018, 1:13 PM
Is there a function on
CoroutineScope
which is
onError
? So in case any of the coroutines in the scope are cancelled or failing it will not cancel the parent scope routines, but instead invoke the error handler. Or is
try-catch
around the
coroutineScope {}
currently the only way?
e

elizarov

10/12/2018, 1:14 PM
There is
CoroutineExceptionHandler
that does it. It is explained here: http://kotlinlang.org/docs/reference/coroutines/exception-handling.html
👍 1
l

lukaswelte

10/12/2018, 1:16 PM
Thanks, but if I have an async function (so I wait for an answer), I would need need a fallback in addition instead of just catching the exception
d

dekans

10/12/2018, 1:20 PM
async
provides a
Deferred
, which can tell you if an exception occured
l

lukaswelte

10/12/2018, 1:22 PM
As an example: https://pl.kotl.in/rk9ZlXAcQ I want that
startFetching
in this example is not cancelling the parent scope and would like to not have
try-catch
around the
startFetching
call, but rather something like
val x = startFetching().ifError { emptyList() }
d

dekans

10/12/2018, 1:25 PM
CoroutineExceptionHandler
seems a good tool for you then
e

elizarov

10/12/2018, 1:25 PM
You can easily write this
ifError
function as an extension.
Copy code
fun <T> Deferred<T>.ifError(defaultValue: () -> T): Deferred<T> = GlobalScope.async { 
    try { await() } catch(e: Throwable) { defaultValue() }
}
But I highly recommend to reconsider the whole design. Writing functions that return
Deferred
is generally a bad idea from the design standpoint. You should design your API using suspending functions, so that you fetching function looks like
suspend fun fetch(): T
, for example
l

lukaswelte

10/12/2018, 1:30 PM
Thank you both, I’ll rethink and prepare a better example (although example does not use
Deferred<T>
but
T
as response)
e

elizarov

10/12/2018, 1:30 PM
In this case Kotlin 1.3 already has the extensions you need:
Write:
Copy code
runCatching { startFetching() }.getOrElse { emptyList() }
But this is not a good design, either, since it ignores all exceptions. So if you have a logic problem somewhere inside your
startFetching
code, you’ll never know about that.
l

lukaswelte

10/12/2018, 3:13 PM
runCatching
is nice. Thank you for your thoughts. I’ll create my own little function which will catch the exception, report/log it and then return the fallback.
👍 1
k

kingsley

10/12/2018, 8:58 PM
Perhaps
supervisorScope
or
SupervisorJob
might also be something to consider for this use case
11 Views