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

hdarritchon

04/18/2019, 1:16 PM
Hi, as I had no answer, I try an other time to ask my question. Thanks for your comprehension and your help. “hi, in my API app, I’d like to decorate (sort of programming by aspect) all my request by a method to compute how long it takes to process it. I need to do some measure. Right now, I am looking at Route interception to do the job but I am quite lost on how it is working (I read the article https://ktor.io/advanced/pipeline/route.html) but sorry, I didn’t manage to make it work. Do you have any clue, hint ou may be a link on a sample ? Is it a good practice to use Route Interception to do this kind of job ?”
d

Dennis Schröder

04/18/2019, 1:21 PM
Not sure if that is what you are looking for. But this handles it already! https://ktor.io/servers/features/metrics.html
h

hdarritchon

04/20/2019, 7:09 AM
Hi @Dennis Schröder Thanks for the hint but I aleady had these on the App. I needed something more precise and accurate in the logging. So I have tried to use the route interceptor and I finally made it 🙂 Please find below my code if it helps someone one day 😉
Copy code
fun Route.routeWithMeasureTime(callback: Route.() -> Unit): Route {
    // With createChild, we create a child node for this received Route
    val routeWithTimeout = this.createChild(object : RouteSelector(1.0) {
        override fun evaluate(context: RoutingResolveContext, segmentIndex: Int): RouteSelectorEvaluation =
            RouteSelectorEvaluation.Constant
    })

    // Intercepts calls from this route at the features step
    routeWithTimeout.intercept(ApplicationCallPipeline.Features) {
        val timeAndReturn = coroutineMeasureTimeAndReturn {
            proceed()
        }

        timeAndReturn.first.record(this.context.request.local)
    }

    // Configure this route with the block provided by the user
    callback(routeWithTimeout)

    return routeWithTimeout
}

suspend fun <T> coroutineMeasureTimeAndReturn(block: suspend CoroutineScope.() -> T): Pair<RequestProcessEvent, T> {
    val start = System.currentTimeMillis()
    val result = coroutineScope { block() }
    val stop = System.currentTimeMillis()


    return Pair(RequestProcessEvent(start, stop), result)
}
RequestProcessEvent is just a class of mine to store data about the execution and log it.
d

Dennis Schröder

04/21/2019, 9:30 AM
Awesome!