agnes-the-ai-analyst/services/ws_gateway/auth.py
Petr f2d3d156e3 Move standalone services from server/ to services/
Extract 4 self-contained services into services/ module:
- server/telegram_bot/ -> services/telegram_bot/
- server/ws_gateway/ -> services/ws_gateway/
- server/corporate_memory/ -> services/corporate_memory/
- server/session_collector.py -> services/session_collector/

Each service now has its own systemd/ directory with .service and .timer files.
deploy.sh updated to auto-discover service units from services/*/systemd/*.

server/ now contains only deployment infrastructure (deploy.sh, setup scripts,
bin/ management tools, sudoers, nginx config).

All imports updated: webapp/app.py, server/bin/ scripts, systemd ExecStart paths.
2026-03-09 12:54:30 +01:00

31 lines
855 B
Python

"""JWT authentication for WebSocket Gateway."""
import logging
import jwt
from .config import DESKTOP_JWT_SECRET
logger = logging.getLogger(__name__)
ALGORITHM = "HS256"
def validate_token(token: str) -> dict | None:
"""Validate a JWT token and return the payload.
Returns the decoded payload dict containing at least "sub" (username)
and "exp" (expiration), or None if the token is invalid.
"""
try:
payload = jwt.decode(token, DESKTOP_JWT_SECRET, algorithms=[ALGORITHM])
if "sub" not in payload:
logger.warning("JWT missing 'sub' claim")
return None
return payload
except jwt.ExpiredSignatureError:
logger.warning("JWT token expired")
return None
except jwt.InvalidTokenError as e:
logger.warning("Invalid JWT token: %s", e)
return None