https://kotlinlang.org logo
#ktor
Title
# ktor
m

Mark Malik

04/20/2022, 3:18 PM
Hello guys, does one know how I would be able to access the ApplicationCall context from outside of te routing handler? Down the line I need to get access to the principal in a service that is being called by a endpoint, passing the principal from the handler is from a design perspective a bad idea in bigger apps. I can try to use the Kotlin Coroutines feature but I’m struggling to find any good examples.
a

Aleksei Tirman [JB]

04/21/2022, 6:40 AM
Could you please explain why is it a bad idea to pass an object from handler to a service?
m

Mark Malik

04/21/2022, 6:43 AM
It’s not a direct usage, it’s down in the 3/4th service that this Principal is needed 🙂 Like I need to access objects based on user permissions, this needs to be checked based on the user id (the principal property). Basically I’m trying to get something like the SecurityContextHolder in Spring. I can access it from everywhere in the app.
I know in Kotlin I should not use ThreadLocal as we don’t share the request per thread so we may get this mixed with other requests, thats why I’m searching for some Coroutines example. Don’t know how I can invoke the launch function with this context not in the handler
@Aleksei Tirman [JB] any ideas?
Or examples 😄
p

Peter

04/21/2022, 12:34 PM
SecurityContextHolder is a bad design, like most things Spring, makes for impure functions everywhere
👍 1
a

Aleksei Tirman [JB]

04/21/2022, 1:21 PM
I’m not sure will it solve your problem or not but if you want to access a principal in a different scope then you can use channels. Here is an example:
Copy code
suspend fun main() = coroutineScope {
    val channel = Channel<Principal>()

    embeddedServer(Netty, port = 12345, host = "0.0.0.0") {
        routing {
            get("/") {
                val principal = object : Principal {}
                channel.send(principal)
                println("response")
                call.respond(HttpStatusCode.OK)
            }
        }
    }.start(wait = false)

    for (principal in channel) {
        println(principal)
    }
}
2 Views