diff --git a/cista/app.py b/cista/app.py index 654e0be..d184b71 100644 --- a/cista/app.py +++ b/cista/app.py @@ -96,7 +96,7 @@ async def persist_auth_session(req, res): existing = getattr(req.ctx, "session", None) if isinstance(existing, dict) and existing.get("username") == username: return - session.create(res, username, secure=req.scheme == "https") + session.create(req, res, username) # Register either SSO proxy or built-in auth routes based on PASKIA_BACKEND_URL diff --git a/cista/auth.py b/cista/auth.py index f7fce87..81ce9f0 100644 --- a/cista/auth.py +++ b/cista/auth.py @@ -1107,7 +1107,7 @@ async def login_page(request): res = html(doc) if s is False: - session.delete(res) + session.delete(request, res) return res @@ -1144,7 +1144,7 @@ async def login_post(request): session.flash(res, "Logged in") else: res = json({"data": {"username": username, "privileged": user.privileged}}) - session.create(res, username, secure=request.scheme == "https") + session.create(request, res, username) return res @@ -1157,7 +1157,7 @@ async def logout_post(request): res.cookies.add_cookie("flash", msg, max_age=5) else: res = json({"message": msg}) - session.delete(res) + session.delete(request, res) return res @@ -1189,7 +1189,7 @@ async def change_password(request): session.flash(res, "Password updated") else: res = json({"message": "Password updated"}) - session.create(res, username, secure=request.scheme == "https") + session.create(request, res, username) return res diff --git a/cista/session.py b/cista/session.py index 8b0d33b..d0fa4b2 100644 --- a/cista/session.py +++ b/cista/session.py @@ -4,6 +4,8 @@ from time import time # In-memory session store: token -> {"username": str, "exp": int} _sessions: dict[str, dict] = {} +SESSION_COOKIE_NAME = "cista" + max_age = 365 * 86400 # Seconds since last login @@ -19,7 +21,7 @@ def _purge_expired() -> None: def get(request): - token = request.cookies.get("s") + token = request.cookies.get(SESSION_COOKIE_NAME) if token is None: return None s = _sessions.get(token) @@ -31,15 +33,24 @@ def get(request): return s -def create(res, username, *, secure: bool = True, **kwargs): +def create(request, res, username, **kwargs): _purge_expired() token = _token() _sessions[token] = {"exp": int(time()) + max_age, "username": username, **kwargs} - res.cookies.add_cookie("s", token, httponly=True, max_age=max_age, secure=secure) + secure = request.scheme == "https" + res.cookies.add_cookie( + SESSION_COOKIE_NAME, + token, + httponly=True, + max_age=max_age, + secure=secure, + host_prefix=secure, + ) -def delete(res): - res.cookies.delete_cookie("s") +def delete(request, res): + secure = request.scheme == "https" + res.cookies.delete_cookie(SESSION_COOKIE_NAME, host_prefix=secure) def flash(res, message: str | None): diff --git a/tests/test_files_auth.py b/tests/test_files_auth.py index 9199e6f..b8b9e3f 100644 --- a/tests/test_files_auth.py +++ b/tests/test_files_auth.py @@ -98,7 +98,7 @@ def _session_cookie_header(username: str) -> dict[str, str]: "exp": int(time()) + session.max_age, "username": username, } - return {"Cookie": f"s={token}"} + return {"Cookie": f"cista={token}"} @pytest.fixture