Luke Rohde
01/27/2020, 6:59 PMhdarritchon
01/27/2020, 7:22 PMval phase = PipelinePhase("doSomeLogging")
pipeline.insertPhaseAfter(ApplicationCallPipeline.Features,phase)
`
With a phase linked after Features, I guess Authentication is done so you can have all you need ?
Feel free to have a look at documentation for more details pipeline phase sequence (https://ktor.io/advanced/pipeline.html#ApplicationCallPipeline)Luke Rohde
01/27/2020, 7:23 PMLuke Rohde
01/27/2020, 7:23 PMLuke Rohde
01/27/2020, 7:24 PMcall.authentication.principal<Principal>()
hdarritchon
01/27/2020, 7:25 PMval phase = PipelinePhase("doSomeLogging") pipeline.insertPhaseBefore(ApplicationCallPipeline.Call,phase)
May be I don’t understand your point, sorry 😞Luke Rohde
01/27/2020, 7:25 PMhdarritchon
01/27/2020, 7:30 PMfun Route.routeEnrichedWithLogData(callback: Route.() -> Unit): Route =
routeWithAction(callback) {
proceed()
MDC.put("principal", this.principal<UserIdPrincipal>()?.name ?: "unknown")
}
`
This way I can log my Principal.hdarritchon
01/27/2020, 7:30 PMhdarritchon
01/27/2020, 7:31 PMinstall(Routing) {
routeEnrichedWithLogData {
val registry = feature(DropwizardMetrics).registry
healthEndPoints()
storageHealthEndPoints()
metricsEndPoints(registry)
...
hdarritchon
01/27/2020, 7:32 PMLuke Rohde
01/27/2020, 7:32 PMLuke Rohde
01/27/2020, 7:33 PMRJ Garcia
03/28/2025, 9:35 PMobject AfterAuthMDCHook : Hook<suspend (ApplicationCall, suspend () -> Unit) -> Unit> {
private val AfterAuthMDCPhase = PipelinePhase("AfterAuthMDCPhase")
override fun install(
pipeline: ApplicationCallPipeline,
handler: suspend (ApplicationCall, suspend () -> Unit) -> Unit,
) {
// AfterAuth phase is inserted after Plugins, before Call should always be after the AfterAuth
pipeline.insertPhaseBefore(ApplicationCallPipeline.Call, AfterAuthMDCPhase)
pipeline.intercept(AfterAuthMDCPhase) {
handler(call, ::proceed)
}
}
}
val LogAuthPrincipal = createRouteScopedPlugin("LogAuthPrincipal") {
on(AfterAuthMDCHook) { call, proceed ->
call.principal<User>?.id?.let { userId ->
withLoggingContextAsync("userId" to userId) { proceed() }
} ?: proceed()
}
}
fun Route.authenticateWithLogContext(
vararg configurations: String? = arrayOf(null),
optional: Boolean = false,
build: Route.() -> Unit,
): Route = authenticate(configurations = configurations, optional = optional) {
install(LogAuthPrincipal)
build()
}
Then within my route, instead of calling authenticate("configuration")
, i'd call authenticateWithLogContext("configuration")