Hi, is there a way to call suspend function inside...
# arrow
d
Hi, is there a way to call suspend function inside
eval's
map and flatmap. I have this code but it doesn't compile as
doSomething()
can only be called withing coroutine body.
Copy code
import arrow.core.Eval
import kotlinx.coroutines.runBlocking

fun main(): Unit = runBlocking {
    Eval.now(10)
        .map { doSomething() }
        .value()
}

private suspend fun doSomething(): Int {
    println("do something")
    return 20
}
s
Hey @ds3fdfd3, It's not possible to call `suspend`'ing code inside
Eval
since it's a deferred execution monad. What is your use case of combining
Eval
with
suspend
?
d
Hi @simon.vergauwen, my use case is something like this. Underlying database library that I am using requires that for transactions, we pass on all the items that we want to put/delete together. To solve this I was trying to write a domain specific method which would take multiple 'Evals' generating put/delete items. However, in certain cases, we have to make another suspending database call from within the domain specific method. E.g. caller provides an Eval which gives a 'deviceId' to be deleted, however, to properly delete this deviceId we need its user, hence we make an internal call to database to get the user. Basically:
eval.map { deviceId ->
val user = getUserForDevice(deviceId) //suspend call
doSomethingWithUserAndDevice(user, deviceId)
}
I hope this makes some sense. 😁
s
I think instead of passing
Eval
around, in this case you'd just want to pass around
suspend () -> A
instead. That way everything is still lazy, and you have full
suspend
support without using a data type like
Eval
. Which doesn't support this usecase.
Eval
is meant to build pure stacksafe functions that cannot be written with
tailrec
.
d
Thanks, I am updating the function with suspend functions rather than
Evals
now. It seems better now.
👌 1