0

I'm trying to use context receivers. I added the freeCompilerArgs = ['-Xcontext-receivers'] to my Kotlin options.

Somehow this code doesn't work and I get a casting exception. It doesn't differ from the MySocket context to the CoroutineScope context.

import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.coroutineScope
import kotlinx.coroutines.flow.flow
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach

class MySocket {
    fun writeToSocket(message: String) {
        println(message)
    }

    fun read() = "message"
}

fun MySocket.response(response: String, originalMessage: String) {
    writeToSocket("response: $response, to: $originalMessage")
}

suspend fun handleClient(
    onMessageReceived: suspend context(MySocket) CoroutineScope.(String) -> Unit
) = coroutineScope {
    val mySocket = MySocket()
    val message = mySocket.read()

    onMessageReceived(mySocket, this, message)
}

suspend fun main() {

    handleClient { originalMessage ->
        flow {
            emit("Some other data from other flow")
        }.onEach { response ->
            response(response, originalMessage)
        }.launchIn(this)
    }
}

I tried switching places between MySocket and CoroutineScope but then I get a casting exception the other way around. I also didn't make the lambda an extension function as follows:

suspend fun handleClient(
    onMessageReceived: suspend context(MySocket, CoroutineScope) (String) -> Unit
) = coroutineScope {
    val mySocket = MySocket()
    val message = mySocket.read()

    onMessageReceived(mySocket, this, message)
}

But then I don't have a direct reference to the coroutine scope (No this inside the lambda):

handleClient { originalMessage ->
    launch {
        flow {
            emit("Some other data from other flow")
        }.collect { response ->
            response(response, originalMessage)
        }
    }
}

0 Answers0