2017-11-14 4 views
3

Ich habe Probleme beim Löschen eines Cookies, das von einer Ktor 0.9.0 serverseitigen Anwendung gesetzt wurde. Vielleicht weiß ich nicht, wie ich es richtig machen soll, oder es gibt eine Lücke im Ktor-Framework.Cookie-Lebenszyklus in Ktor 0.9.0 Servlet steuern

Cookie erstellen und löschen ist nicht das Problem per se, aber um ein Cookie zu löschen, muss ich den gleichen Pfad verwenden, der mit dem Cookie auf dem Client-Browser gespeichert ist. Ktor lass mich den Weg mit der Cookie-Erstellung steuern. Hier ist meine Konfiguration:

install(Sessions) { 
    cookie<MySession>(sessionMarker) { 
     cookie.duration = cookieDuration 
     cookie.path = "/myWebapp" 
     transform(SessionTransportTransformerMessageAuthentication(sessionKey)) 
    } 
} 

auf der Anmeldeseite /myWebapp/page/login schaffe ich das Cookie, das dann an den Client gesendet wird, und es bewegt sich hin und her für den Rest der Anforderungen an die Web-Anwendung gesendet:

call.sessions.set(MySession([some data class arguments])) 

Der Cookie zeigt den Pfad /myWebapp bei der Überprüfung auf dem Client. Der Standardwert wäre /myWebapp/page, da dies der Pfad der Anmeldeseite ist, der Pfad jedoch aus der oben gezeigten Cookie-Konfiguration stammt. Bis jetzt ist alles gut.

Schließlich wird der Benutzer möchte über eine POST-Anforderung an die Login-Seite, um sich abzumelden:

call.sessions.clear<MySession>() 

Das hier Problem ist, dass ich keine Möglichkeit der Kontrolle der Cookie-Pfad gefunden haben. Da die Anmeldeseite /myWebapp/page/login das abgelaufene Cookie für einen anderen Pfad an den Client zurücksendet (eigene /myWebapp/page), wird das ursprüngliche Cookie nicht gelöscht (/myWebapp/page! = /myWebapp).

Wie kann ich den Pfad des Cookies in Ktor 0.9.0 kontrollieren, wenn ich versuche, ihn zu löschen?

Ich weiß, wie man es umgehen kann: durch Erstellen des Cookies mit dem gleichen Pfad von wo ich es löschen werde. Aber das ist nicht, was ich will (es gibt andere Wege innerhalb der Web-Anwendungen wie /myWebapp/others waren die Cookies sollten verwendet werden). Die Möglichkeit, den Pfad des Cookies während der Erstellung zu kontrollieren, macht keinen Sinn.

Antwort

1

Ich denke, Sie könnten versuchen, Ihren eigenen benutzerdefinierten SessionTransportCookie zu erstellen.

Wenn Sie tiefer in Methode sehen cookie<MySession>(sessionMarker) Sie diesen Code finden:

inline fun <reified S : Any> Sessions.Configuration.cookie(name: String, block: CookieSessionBuilder<S>.() -> Unit): Unit = cookie(name, S::class, block) 

inline fun <S : Any> Sessions.Configuration.cookie(name: String, sessionType: KClass<S>, block: CookieSessionBuilder<S>.() -> Unit) { 
    val builder = CookieSessionBuilder(sessionType).apply(block) 
    val transport = SessionTransportCookie(name, builder.cookie, builder.transformers) 
    val tracker = SessionTrackerByValue(sessionType, builder.serializer) 
    val provider = SessionProvider(name, sessionType, transport, tracker) 
    register(provider) 
} 

Wichtige Linie ist hier die Schaffung Sitzung Transport Cookie Zeile: SessionTransportCookie(name, builder.cookie, builder.transformers)

Lässt tiefer schauen in SessionTransportCookie:

class SessionTransportCookie(val name: String, 
          val configuration: CookieConfiguration, 
          val transformers: List<SessionTransportTransformer> 
) : SessionTransport { 

    override fun receive(call: ApplicationCall): String? { 
     return transformers.transformRead(call.request.cookies[name]) 
    } 

    override fun send(call: ApplicationCall, value: String) { 
     val now = LocalDateTime.now() 
     val expires = now.plus(configuration.duration) 
     val maxAge = configuration.duration[ChronoUnit.SECONDS].toInt() 
     val cookie = Cookie(name, 
       transformers.transformWrite(value), 
       configuration.encoding, 
       maxAge, 
       expires, 
       configuration.domain, 
       configuration.path, 
       configuration.secure, 
       configuration.httpOnly, 
       configuration.extensions 
     ) 

     call.response.cookies.append(cookie) 
    } 

    override fun clear(call: ApplicationCall) { 
     call.response.cookies.appendExpired(name) 
    } 
} 

class CookieConfiguration { 
    var duration: TemporalAmount = Duration.ofDays(7) 
    var encoding: CookieEncoding = CookieEncoding.URI_ENCODING 
    var domain: String? = null 
    var path: String? = null 
    var secure: Boolean = false 
    var httpOnly: Boolean = false 
    val extensions: MutableMap<String, String?> = mutableMapOf() 
} 

Also, wie Sie sehen, in dieser Klasse haben Sie alle Möglichkeiten, Ihre CookiesanzupassenLogik.