feat: Implement session management with middleware and update authentication flow
This commit is contained in:
@@ -1,15 +1,19 @@
|
||||
from __future__ import annotations
|
||||
|
||||
from collections.abc import Iterator
|
||||
from typing import cast
|
||||
from urllib.parse import parse_qs, urlparse
|
||||
|
||||
import pytest
|
||||
from fastapi import FastAPI
|
||||
from fastapi.testclient import TestClient
|
||||
from sqlalchemy import select
|
||||
from sqlalchemy.orm import Session, sessionmaker
|
||||
|
||||
from models import Role, User, UserRole
|
||||
from dependencies import get_auth_session, require_current_user
|
||||
from services.security import hash_password
|
||||
from services.session import AuthSession, SessionTokens
|
||||
|
||||
|
||||
@pytest.fixture()
|
||||
@@ -223,7 +227,8 @@ class TestPasswordResetFlow:
|
||||
data={"email": "mismatch@example.com"},
|
||||
follow_redirects=False,
|
||||
)
|
||||
token = parse_qs(urlparse(request_response.headers["location"]).query)["token"][0]
|
||||
token = parse_qs(urlparse(request_response.headers["location"]).query)[
|
||||
"token"][0]
|
||||
|
||||
submit_response = client.post(
|
||||
"/reset-password",
|
||||
@@ -236,4 +241,46 @@ class TestPasswordResetFlow:
|
||||
)
|
||||
|
||||
assert submit_response.status_code == 400
|
||||
assert "Passwords do not match" in submit_response.text
|
||||
assert "Passwords do not match" in submit_response.text
|
||||
|
||||
|
||||
class TestLogoutFlow:
|
||||
def test_logout_clears_cookies_and_redirects(
|
||||
self,
|
||||
client: TestClient,
|
||||
db_session: Session,
|
||||
) -> None:
|
||||
user = User(
|
||||
email="logout@example.com",
|
||||
username="logoutuser",
|
||||
password_hash=hash_password("SecureP@ss1"),
|
||||
is_active=True,
|
||||
)
|
||||
db_session.add(user)
|
||||
db_session.commit()
|
||||
|
||||
session = AuthSession(
|
||||
tokens=SessionTokens(
|
||||
access_token="access-token",
|
||||
refresh_token="refresh-token",
|
||||
access_token_source="cookie",
|
||||
),
|
||||
user=user,
|
||||
)
|
||||
|
||||
app = cast(FastAPI, client.app)
|
||||
app.dependency_overrides[require_current_user] = lambda: user
|
||||
app.dependency_overrides[get_auth_session] = lambda: session
|
||||
|
||||
try:
|
||||
response = client.get("/logout", follow_redirects=False)
|
||||
finally:
|
||||
app.dependency_overrides.pop(require_current_user, None)
|
||||
app.dependency_overrides.pop(get_auth_session, None)
|
||||
|
||||
assert response.status_code == 303
|
||||
location = response.headers.get("location")
|
||||
assert location and location.startswith("http://testserver/login")
|
||||
set_cookie_header = response.headers.get("set-cookie") or ""
|
||||
assert "calminer_access_token=" in set_cookie_header
|
||||
assert "Max-Age=0" in set_cookie_header or "expires=" in set_cookie_header.lower()
|
||||
|
||||
Reference in New Issue
Block a user