From 99251b41c3485892a1fb3ab6f147081e143e2393 Mon Sep 17 00:00:00 2001 From: floriankirmaier Date: Fri, 3 Jan 2025 11:49:22 +0100 Subject: [PATCH] small routing bugfix --- .../sessionmanager/TestSessionManager.scala | 25 +++++++++++++++++++ .../one/jpro/platform/routing/Response.scala | 2 ++ .../sessionmanager/SessionManager.scala | 18 +++++++------ .../SessionManagerDesktop.scala | 3 ++- .../sessionmanager/SessionManagerDummy.scala | 4 +-- .../sessionmanager/SessionManagerWeb.scala | 4 ++- 6 files changed, 45 insertions(+), 11 deletions(-) diff --git a/jpro-routing/core-test/src/test/scala/one/jpro/platform/routing/sessionmanager/TestSessionManager.scala b/jpro-routing/core-test/src/test/scala/one/jpro/platform/routing/sessionmanager/TestSessionManager.scala index a550e307..a61e6d5c 100644 --- a/jpro-routing/core-test/src/test/scala/one/jpro/platform/routing/sessionmanager/TestSessionManager.scala +++ b/jpro-routing/core-test/src/test/scala/one/jpro/platform/routing/sessionmanager/TestSessionManager.scala @@ -1,6 +1,9 @@ package one.jpro.platform.routing.sessionmanager +import javafx.scene.control.Label +import one.jpro.platform.routing.{Response, Route, RouteApp} import org.junit.jupiter.api.Test +import simplefx.core._ class TestSessionManager { @Test @@ -11,4 +14,26 @@ class TestSessionManager { assert(SessionManager.mergeURLs("http://a.com/b/c", "../d") == "http://a.com/d") assert(SessionManager.mergeURLs("http://a/b", "/") == "http://a/") } + + @Test + def testRedirects(): Unit = { + val route = Route.empty() + .and(Route.get("/",r => Response.node(new Label("Empty")))) + .path("/test", Route.empty() + .and(Route.redirect("/","./test2")) + .and(Route.get("/test2", r => Response.node(new Label("Yes")))) + ) + + val app = new RouteApp { + override def createRoute(): Route = route + } + val stage = inFX(new javafx.stage.Stage()) + inFX(app.start(stage)) + + val res = inFX(app.getSessionManager().gotoURL("/test/").future).await + inFX { + val url = app.getSessionManager().getURL() + assert(url == "/test/test2") + } + } } diff --git a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/Response.scala b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/Response.scala index eeb94570..3afb564e 100644 --- a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/Response.scala +++ b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/Response.scala @@ -8,9 +8,11 @@ case class Response(future: FXFuture[ResponseResult]) { object Response { def empty(): Response = Response(FXFuture.unit(null)) def redirect(to: String): Response = Response(FXFuture.unit(Redirect(to))) + def error(ex: Exception): Response = Response(FXFuture.error(ex)) def view(view: View): Response = Response(FXFuture.unit(view)) def node(node: javafx.scene.Node): Response = Response(FXFuture.unit(View.fromNode(node))) def fromFuture(future: FXFuture[Response]): Response = Response(future.flatMap(_.future)) + def fromResult(result: ResponseResult): Response = Response(FXFuture.unit(result)) def fromFutureResult(future: FXFuture[ResponseResult]): Response = Response(future) } diff --git a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManager.scala b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManager.scala index 2b9aca20..e5b1e48e 100644 --- a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManager.scala +++ b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManager.scala @@ -32,39 +32,43 @@ trait SessionManager { THIS => @Bind var url: String = null @Bind var view: View = null + def getURL(): String = url + def goBack(): Unit def goForward(): Unit def isExternal(x: String): Boolean = x.startsWith("http") - def gotoURL(url: String): Unit = { + def gotoURL(url: String): Response = { if(isExternal(url)) { if(WebAPI.isBrowser) { this.asInstanceOf[SessionManagerWeb].webAPI.executeScript(s"""window.location.href = "$url";""") } else { SessionManager.externalLinkImpl.accept(url) } + Response.redirect(url) } else { gotoURL(url,true) } } - def gotoURL(url: String, pushState: Boolean = true): Unit = { + def gotoURL(url: String, pushState: Boolean = true): Response = { val url2 = SessionManager.mergeURLs(THIS.url, url) try { - logger.debug(s"goto: $url") - val request = getRequest(url) + logger.debug(s"goto: $url2") + val request = getRequest(url2) val newView = if(view != null && view.handleRequest(request)) Response(FXFuture(view)) else { webApp.getRoute()(request) } - newView.future.map { response => + Response.fromFuture(newView.future.map { response => assert(response != null, s"Response for $url2 was null") this.url = url2 gotoURL(url2, response, pushState) - } + }) } catch { case ex: Exception => logger.error(s"Error while loading the path $url2", ex) + Response.error(ex) } } - def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Unit + def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Response def getRequest(url: String): Request = { val node = if(view == null) null else view.realContent diff --git a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDesktop.scala b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDesktop.scala index 68758542..7d7abe1b 100644 --- a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDesktop.scala +++ b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDesktop.scala @@ -26,7 +26,7 @@ class SessionManagerDesktop(val webApp: RouteNode) extends SessionManager { THIS gotoURL(historyCurrent.path, false) } - def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Unit = { + def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Response = { x match { case Redirect(url) => logger.debug(s"redirect: ${_url} -> $url") @@ -54,6 +54,7 @@ class SessionManagerDesktop(val webApp: RouteNode) extends SessionManager { THIS } historyCurrent = HistoryEntry(url, view.title) } + Response.view(view) } } val container = new StackPane() diff --git a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDummy.scala b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDummy.scala index 84a08c5b..c957bce4 100644 --- a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDummy.scala +++ b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerDummy.scala @@ -8,8 +8,8 @@ class SessionManagerDummy(val webApp: RouteNode) extends SessionManager { override def goForward(): Unit = () - override def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Unit = { - + override def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Response = { + Response.fromResult(x) } override def start(): Unit = () diff --git a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerWeb.scala b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerWeb.scala index 6dbe8e20..12e13839 100644 --- a/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerWeb.scala +++ b/jpro-routing/core/src/main/scala/one/jpro/platform/routing/sessionmanager/SessionManagerWeb.scala @@ -33,13 +33,14 @@ class SessionManagerWeb(val webApp: RouteNode, val webAPI: WebAPI) extends Sessi }) } - def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Unit = { + def gotoURL(_url: String, x: ResponseResult, pushState: Boolean): Response = { assert(x != null, "Response was null for url: " + _url) val url = _url x match { case Redirect(url) => if(isExternal(url)) { this.asInstanceOf[SessionManagerWeb].webAPI.executeScript(s"""window.location.href = "$url";""") + Response.fromResult(x) } else { gotoURL(url) } @@ -81,6 +82,7 @@ class SessionManagerWeb(val webApp: RouteNode, val webAPI: WebAPI) extends Sessi webAPI.executeScript(s"""document.title = "${view.title.replace("\"","\\\"")}";""") webAPI.executeScript(s"""document.querySelector('meta[name="description"]').setAttribute("content", "${view.description.replace("\"","\\\"")}");""") webAPI.executeScript(s"history.replaceState($initialState, null, null)") + Response.fromResult(x) } }