Has anyone experienced anything like this, i using...
# mvikotlin
m
Has anyone experienced anything like this, i using
mvikotlin-extensions-coroutines
Copy code
kotlin.IllegalStateException: There is no event loop. Use runBlocking { ... } to start one.
kfun:kotlin.Throwable#<init>(kotlin.String?){} + 95
kfun:kotlin.Exception#<init>(kotlin.String?){} + 93
kfun:kotlin.RuntimeException#<init>(kotlin.String?){} + 93
kfun:kotlin.IllegalStateException#<init>(kotlin.String?){} + 93
kfun:kotlinx.coroutines.takeEventLoop#internal + 532
kfun:kotlinx.coroutines.DefaultExecutor#dispatch(kotlin.coroutines.CoroutineContext;kotlinx.coroutines.Runnable){} + 204
kfun:kotlinx.coroutines.NativeMainDispatcher.dispatch#internal + 275
kfun:kotlinx.coroutines.internal#resumeCancellableWith__at__kotlin.coroutines.Continuation<0:0>(kotlin.Result<0:0>;kotlin.Function1<kotlin.Throwable,kotlin.Unit>?){0§<kotlin.Any?>} + 1275
kfun:kotlinx.coroutines.intrinsics#startCoroutineCancellable__at__kotlin.coroutines.SuspendFunction1<0:0,0:1>(0:0;kotlin.coroutines.Continuation<0:1>;kotlin.Function1<kotlin.Throwable,kotlin.Unit>?){0§<kotlin.Any?>;1§<kotlin.Any?>} + 671
kfun:kotlinx.coroutines.intrinsics#startCoroutineCancellable$default__at__kotlin.coroutines.SuspendFunction1<0:0,0:1>(0:0;kotlin.coroutines.Continuation<0:1>;kotlin.Function1<kotlin.Throwable,kotlin.Unit>?;kotlin.Int){0§<kotlin.Any?>;1§<kotlin.Any?>} + 370
kfun:kotlinx.coroutines.CoroutineStart#invoke(kotlin.coroutines.SuspendFunction1<0:0,0:1>;0:0;kotlin.coroutines.Continuation<0:1>){0§<kotlin.Any?>;1§<kotlin.Any?>} + 693
kfun:kotlinx.coroutines.AbstractCoroutine#start(kotlinx.coroutines.CoroutineStart;0:0;kotlin.coroutines.SuspendFunction1<0:0,1:0>){0§<kotlin.Any?>} + 162
kfun:kotlinx.coroutines#launch__at__kotlinx.coroutines.CoroutineScope(kotlin.coroutines.CoroutineContext;kotlinx.coroutines.CoroutineStart;kotlin.coroutines.SuspendFunction1<kotlinx.coroutines.CoroutineScope,kotlin.Unit>){}kotlinx.coroutines.Job + 666
kfun:kotlinx.coroutines#launch$default__at__kotlinx.coroutines.CoroutineScope(kotlin.coroutines.CoroutineContext?;kotlinx.coroutines.CoroutineStart?;kotlin.coroutines.SuspendFunction1<kotlinx.coroutines.CoroutineScope,kotlin.Unit>;kotlin.Int){}kotlinx.coroutines.Job + 697
kfun:com.arkivanov.mvikotlin.extensions.coroutines.SuspendExecutor#handleAction(1:1){} + 364
kfun:com.arkivanov.mvikotlin.main.store.DefaultStore.<init>$lambda-0#internal + 281
kfun:com.arkivanov.mvikotlin.main.store.DefaultStore.$<init>$lambda-0$FUNCTION_REFERENCE$1.invoke#internal + 97
kfun:com.arkivanov.mvikotlin.main.store.DefaultStore.$<init>$lambda-0$FUNCTION_REFERENCE$1.$<bridge-UNNN>invoke(-1:0){}#internal + 97
kfun:com.arkivanov.mvikotlin.core.store.SimpleBootstrapper#invoke(){} + 686
kfun:com.arkivanov.mvikotlin.main.store.DefaultStore#<init>(1:3;com.arkivanov.mvikotlin.core.store.Bootstrapper<1:1>?;kotlin.Function0<com.arkivanov.mvikotlin.core.store.Executor<1:0,1:1,1:3,1:2,1:4>>;com.arkivanov.mvikotlin.core.store.Reducer<1:3,1:2>){} + 1682
kfun:com.arkivanov.mvikotlin.main.store.DefaultStoreFactory#create(kotlin.String?;0:3;com.arkivanov.mvikotlin.core.store.Bootstrapper<0:1>?;kotlin.Function0<com.arkivanov.mvikotlin.core.store.Executor<0:0,0:1,0:3,0:2,0:4>>;com.arkivanov.mvikotlin.core.store.Reducer<0:3,0:2>){0§<kotlin.Any>;1§<kotlin.Any>;2§<kotlin.Any>;3§<kotlin.Any>;4§<kotlin.Any>}com.arkivanov.mvikotlin.core.store.Store<0:0,0:3,0:4> + 476
a
I think this question is more related to to coroutines. Perhaps this should help: https://stackoverflow.com/questions/66917563/kmm-on-ios-there-is-no-event-loop-use-runblocking-to-start-one
Stable coroutines version does not support multithreading, there is no DefaultDispatcher nor IO dispatcher. If you need multithreading, you need to use either the unstable
native-mt
version of coroutines, or Reaktive.
n
Recommended Reaktive
m
thanks @Arkadii Ivanov & @Nikola Milovic
how to adopt reaktive for existing project, im using ktor with coroutine suspend. until level useCase with suspend function,
Copy code
abstract class UseCase<SuccessType : Any, ErrorType : Any, in Params> {

    abstract suspend fun build(params: Params?): NetworkResponse<SuccessType, ErrorType>

}
and i change from
Copy code
SuspendExecutor
to
Copy code
private inner class ExecutorImpl :
    ReaktiveExecutor<Nothing, Unit, LauncherState, Result, LauncherSideEffect>()
how to call suspend fun on executor without freeze..?
a
You will need to use MVIKotlin Reaktive extensions instead of coroutines. Check out the docs: https://arkivanov.github.io/MVIKotlin/store.html Also if you are going to mix reaktive and coroutines then you should read Reaktive readme carefully: https://github.com/badoo/Reaktive#coroutines-interop In general I recommend to not heavily mix them. You can just use
singleFromCoroutine {}
for Ktor calls, and keep everything else with Reaktive. But up to you. The key point is that Ktor by default requires
native-mt
coroutines, it will crash with the stable version. So you will have to use Reaktive
coroutines-interop
module with
-with
version suffix. This version is specifically for
native-mt
coroutines.
n
Copy code
singleFromCoroutine {
    /*
     * This block will be executed inside `runBlocking` in Kotlin/Native.
     * Please avoid using Ktor here, it may crash.
     */
}
@Arkadii Ivanov I've only seen examples that use singleFromCoroutine to enable Ktor and Reaktive compatibility but right here in the docs it's stated it can cause crashes? Any input on this? Okay nevermind, there seems to be an issue to update the docs
a
There are two versions of the coroutine interop module, regular and
-nmtc
. The latter works with multithreaded coroutines variant, the one that is also used by Ktor. It should work fine. https://github.com/badoo/Reaktive#coroutines-interop-based-on-multi-threaded-kotlinxcoroutines