Skip to content

Nested coroutineBinding crash #128

@dbottillo

Description

@dbottillo

👋 I just came across a crash when dealing with nested coroutineBinding and would like to know what's your view on how to solve it.

The simplest way to reproduce is to take the example from the doc and wrap one of the coroutines inside a coroutineBinding:

suspend fun failsIn1ms(): Result<Int, String> {
    delay(1000)
    return Err("error")
}

suspend fun succeedIn5ms(): Result<Int, String> {
    delay(5000)
    return Ok(5)
}
suspend fun succeedIn5msWrapper() = coroutineBinding {
    succeedIn5ms().bind()
}

fun main() {
    runBlocking {
        val res = coroutineBinding {
            val x =  async { succeedIn5msWrapper().bind() }
            val y = async { failsIn1ms().bind() }
            x.await() + y.await()
        }
        res.onSuccess {
            println("success: $it")
        }.onFailure {
            println("failure: $it")
        }
    }
}

This code will crash at runtime with a NPE at this line inside coroutineBinding. I think what's happening is that failsIn1ms() is throwing a BindCancellationException which gets propagate to the parent which then notify its children but then succeedIn5msWrapper() is receiving a BindCancellationException which is from another coroutine and receiver.result!! is null at that stage.

One way to solve it is to wrap each bind() call with its own scope but that doesn't feel completely right as that doesn't seem a scalable solution, you can't just know how how many coroutineBinding() nested binding there could be. Another option is to do receiver.result ?: throw ex instead and basically saying that if result is null then this is just another exception that doesn't belong to this coroutineBinding.

Are there any other better solution?

Thanks!

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions