Exception thrown by deferred.await() within a runBlocking treated as unhandled even after caught

前端 未结 4 1020
时光说笑
时光说笑 2021-02-14 10:20

This code:

fun main() {
    runBlocking {
        try {
            val deferred = async { throw Exception() }
            deferred.await()
        } catch (e: E         


        
4条回答
  •  隐瞒了意图╮
    2021-02-14 10:44

    This can be resolved by slightly altering the code to make the deferred value be executed explicitly using the same CoroutineContext as the runBlocking scope, e.g.

    runBlocking {
        try {
            val deferred = withContext(this.coroutineContext) {
                async {
                    throw Exception()
                }
            }
            deferred.await()
        } catch (e: Exception) {
            println("Caught $e")
        }
    }
    println("Completed")
    

    UPDATE AFTER ORIGINAL QUESTION UPDATED

    Does this provide what you want:

    runBlocking {
        supervisorScope {
            try {
                val a = async {
                    delay(1000)
                    println("Done after delay")
                }
                val b = async { throw Exception() }
                awaitAll(a, b)
            } catch (e: Exception) {
                println("Caught $e")
                // Optional next line, depending on whether you want the async with the delay in it to be cancelled.
                coroutineContext.cancelChildren()
            }
        }
    }
    

    This is taken from this comment which discusses parallel decomposition.

提交回复
热议问题