Initial commit: CI Agent competitive-intelligence monitoring app

FastAPI + Celery + Next.js + Postgres/Redis app with company monitoring,
source collection, LLM-based change analysis, enrichment, and account
security (Turnstile, escalating lockout, email verification).
This commit is contained in:
2026-08-05 10:48:20 -04:00
commit 1a4c80958f
365 changed files with 43541 additions and 0 deletions
+254
View File
@@ -0,0 +1,254 @@
"""Auth flow tests. Runs under AUTH_MODE=jwt (the suite default) except where
`local_mode_client` explicitly exercises the local-dev-user path."""
from __future__ import annotations
import uuid
from datetime import UTC, datetime, timedelta
from fastapi.testclient import TestClient
from app.core.config import get_settings
from app.main import app
from app.models.enums import SecurityEventType
from app.models.user import LOCAL_DEV_USER_ID
from app.repositories.user_security_event_repository import UserSecurityEventRepository
def _unique_email() -> str:
return f"user-{uuid.uuid4().hex[:12]}@example.com"
def test_register_then_login(client):
email = _unique_email()
register_resp = client.post(
"/api/v1/auth/register",
json={
"email": email,
"password": "correct-horse-1",
"display_name": "Test User",
},
)
assert register_resp.status_code == 201
body = register_resp.json()
assert body["email"] == email
assert "password" not in body
assert "password_hash" not in body
login_resp = client.post(
"/api/v1/auth/login", json={"email": email, "password": "correct-horse-1"}
)
assert login_resp.status_code == 200
tokens = login_resp.json()
assert tokens["access_token"]
assert tokens["refresh_token"]
assert tokens["token_type"] == "bearer"
def test_register_duplicate_email_conflicts(client):
email = _unique_email()
payload = {"email": email, "password": "correct-horse-1", "display_name": "Test User"}
first = client.post("/api/v1/auth/register", json=payload)
assert first.status_code == 201
second = client.post("/api/v1/auth/register", json=payload)
assert second.status_code == 409
def test_register_rejects_weak_password(client):
resp = client.post(
"/api/v1/auth/register",
json={"email": _unique_email(), "password": "allletters", "display_name": "Test User"},
)
assert resp.status_code == 422
def test_login_wrong_password_rejected(client):
email = _unique_email()
client.post(
"/api/v1/auth/register",
json={"email": email, "password": "correct-horse-1", "display_name": "Test User"},
)
resp = client.post("/api/v1/auth/login", json={"email": email, "password": "wrong-password-1"})
assert resp.status_code == 401
def test_me_requires_bearer_token(client):
resp = client.get("/api/v1/auth/me")
assert resp.status_code == 401
def test_me_returns_current_user(client):
email = _unique_email()
client.post(
"/api/v1/auth/register",
json={"email": email, "password": "correct-horse-1", "display_name": "Test User"},
)
login = client.post(
"/api/v1/auth/login", json={"email": email, "password": "correct-horse-1"}
).json()
resp = client.get(
"/api/v1/auth/me", headers={"Authorization": f"Bearer {login['access_token']}"}
)
assert resp.status_code == 200
body = resp.json()
assert body["email"] == email
assert body["auth_mode"] == "jwt"
def test_refresh_rotates_and_invalidates_old_token(client):
email = _unique_email()
client.post(
"/api/v1/auth/register",
json={"email": email, "password": "correct-horse-1", "display_name": "Test User"},
)
login = client.post(
"/api/v1/auth/login", json={"email": email, "password": "correct-horse-1"}
).json()
refresh_resp = client.post(
"/api/v1/auth/refresh", json={"refresh_token": login["refresh_token"]}
)
assert refresh_resp.status_code == 200
new_tokens = refresh_resp.json()
assert new_tokens["refresh_token"] != login["refresh_token"]
# The old refresh token was rotated out and must not be reusable.
reuse_resp = client.post("/api/v1/auth/refresh", json={"refresh_token": login["refresh_token"]})
assert reuse_resp.status_code == 401
def test_logout_revokes_refresh_token(client):
email = _unique_email()
client.post(
"/api/v1/auth/register",
json={"email": email, "password": "correct-horse-1", "display_name": "Test User"},
)
login = client.post(
"/api/v1/auth/login", json={"email": email, "password": "correct-horse-1"}
).json()
logout_resp = client.post("/api/v1/auth/logout", json={"refresh_token": login["refresh_token"]})
assert logout_resp.status_code == 204
reuse_resp = client.post("/api/v1/auth/refresh", json={"refresh_token": login["refresh_token"]})
assert reuse_resp.status_code == 401
def test_local_mode_me_returns_fixed_dev_user_without_token(local_mode_client):
resp = local_mode_client.get("/api/v1/auth/me")
assert resp.status_code == 200
body = resp.json()
assert body["email"] == "[email protected]"
assert body["auth_mode"] == "local"
def test_register_login_available_even_in_local_mode(local_mode_client):
"""Registering/logging in a real account must always be possible,
regardless of AUTH_MODE - the loopback convenience only affects whether
a request can skip auth entirely, not whether real accounts exist."""
email = _unique_email()
register_resp = local_mode_client.post(
"/api/v1/auth/register",
json={"email": email, "password": "correct-horse-1", "display_name": "X"},
)
assert register_resp.status_code == 201
login_resp = local_mode_client.post(
"/api/v1/auth/login", json={"email": email, "password": "correct-horse-1"}
)
assert login_resp.status_code == 200
assert login_resp.json()["access_token"]
def test_security_events_requires_auth(client):
resp = client.get("/api/v1/auth/security-events")
assert resp.status_code == 401
def _login_success_count(events: list[dict]) -> int:
return sum(1 for e in events if e["event_type"] == "login_success")
def test_local_dev_sign_in_is_logged_to_account_activity(local_mode_client):
"""The local-dev bypass has no real login step - hitting any
authenticated endpoint (here /auth/me, the same check the frontend
performs on app load) must still show up as a sign-in."""
local_mode_client.get("/api/v1/auth/me")
events = local_mode_client.get("/api/v1/auth/security-events").json()
assert any(e["event_type"] == "login_success" for e in events)
def test_local_dev_sign_in_is_not_logged_twice_within_cooldown(local_mode_client):
"""Every authenticated request runs get_or_create_local_user - without
a cooldown, browsing the app at all would flood Account activity with
one login_success per request."""
local_mode_client.get("/api/v1/auth/me")
before = _login_success_count(local_mode_client.get("/api/v1/auth/security-events").json())
local_mode_client.get("/api/v1/auth/me")
after = _login_success_count(local_mode_client.get("/api/v1/auth/security-events").json())
assert after == before
async def test_local_dev_sign_in_logs_again_after_cooldown_expires(local_mode_client, db_session):
local_mode_client.get("/api/v1/auth/me")
before = _login_success_count(local_mode_client.get("/api/v1/auth/security-events").json())
event_repo = UserSecurityEventRepository(db_session)
last_login = await event_repo.most_recent_of_type(
LOCAL_DEV_USER_ID, SecurityEventType.LOGIN_SUCCESS
)
assert last_login is not None
last_login.created_at = datetime.now(UTC) - timedelta(minutes=31)
await db_session.commit()
local_mode_client.get("/api/v1/auth/me")
after = _login_success_count(local_mode_client.get("/api/v1/auth/security-events").json())
assert after == before + 1
def test_security_events_returns_own_login_events_only(client):
email_a = _unique_email()
client.post(
"/api/v1/auth/register",
json={"email": email_a, "password": "correct-horse-1", "display_name": "A"},
)
login_a = client.post(
"/api/v1/auth/login", json={"email": email_a, "password": "correct-horse-1"}
).json()
email_b = _unique_email()
client.post(
"/api/v1/auth/register",
json={"email": email_b, "password": "correct-horse-1", "display_name": "B"},
)
client.post("/api/v1/auth/login", json={"email": email_b, "password": "correct-horse-1"})
resp = client.get(
"/api/v1/auth/security-events",
headers={"Authorization": f"Bearer {login_a['access_token']}"},
)
assert resp.status_code == 200
events = resp.json()
event_types = {e["event_type"] for e in events}
# registration writes email_verification_sent, login writes login_success -
# both belong to user A only, never user B's events.
assert event_types == {"email_verification_sent", "login_success"}
def test_local_mode_setting_alone_does_not_bypass_auth_for_non_loopback_callers():
"""AUTH_MODE=local is not a blanket switch - a request that isn't
actually from loopback (e.g. a LAN/WAN caller, or here Starlette's
TestClient default fake peer) still needs a real bearer token."""
settings = get_settings().model_copy(update={"auth_mode": "local"})
app.dependency_overrides[get_settings] = lambda: settings
try:
with TestClient(app) as non_loopback_client: # default peer: ("testclient", 50000)
resp = non_loopback_client.get("/api/v1/auth/me")
assert resp.status_code == 401
finally:
app.dependency_overrides.pop(get_settings, None)