diff --git a/packages/server/src/server/routes/auth-pages/login.html b/packages/server/src/server/routes/auth-pages/login.html index c3f95ac8..5dea9c70 100644 --- a/packages/server/src/server/routes/auth-pages/login.html +++ b/packages/server/src/server/routes/auth-pages/login.html @@ -119,7 +119,8 @@ showError(message || `Login failed (${res.status})`) return } - window.location.href = "/" + // Replace history entry so Back doesn't return to /login. + window.location.replace("/") } catch (e) { showError(e && e.message ? e.message : String(e)) } diff --git a/packages/server/src/server/routes/auth.ts b/packages/server/src/server/routes/auth.ts index e47da74a..6bb7d3d3 100644 --- a/packages/server/src/server/routes/auth.ts +++ b/packages/server/src/server/routes/auth.ts @@ -51,7 +51,19 @@ function getTokenHtml(): string { } export function registerAuthRoutes(app: FastifyInstance, deps: RouteDeps) { - app.get("/login", async (_request, reply) => { + app.get("/login", async (request, reply) => { + // If already authenticated, don't show the login page. + const session = deps.authManager.getSessionFromRequest(request) + if (session) { + reply.redirect("/") + return + } + + // Avoid caching the login page (helps with bfcache/back behavior). + reply.header("Cache-Control", "no-store") + reply.header("Pragma", "no-cache") + reply.header("Expires", "0") + const status = deps.authManager.getStatus() reply.type("text/html").send(getLoginHtml(status.username)) }) @@ -67,6 +79,11 @@ export function registerAuthRoutes(app: FastifyInstance, deps: RouteDeps) { return } + // Avoid caching the token bootstrap page. + reply.header("Cache-Control", "no-store") + reply.header("Pragma", "no-cache") + reply.header("Expires", "0") + reply.type("text/html").send(getTokenHtml()) })