- Moved Anilist errors to its own module and gave them status codes and messages that can propagate upstream

- Created exception handler to propagate erros
This commit is contained in:
florian committed 2026-11-04 13:02:53 +01:00
1 parent 79e8de124a
commit be2e0857e4
5 files changed
+280 -75

No files matched your search

+8 -31
View File
@@ -8,7 +8,7 @@ from fastapi import APIRouter, Depends, FastAPI, HTTPException, Request
from seadex import EntryNotFoundError, SeaDexEntry
from service_auth import UserId
from anilist_query import AniListError, AnimeNotFoundError, MissingAnimeName, get_anime_name
from anilist_query import get_anime_name
from auth_config import Caller, auth
from db_module import (
close_connection_pool,
@@ -16,11 +16,12 @@ from db_module import (
get_db,
start_healthcheck_thread,
)
from metrics_server import REQUEST_COUNTER, metrics_api
from handlers import register_handlers
from metrics_server import metrics_api
from models import AnimeCreate, AnimeEntry, AnimeList
from secret_manager import cleanup_secret_files
from send_notifications import NotificationClient, NotificationUnavailableError, NotificationError
from send_notifications import NotificationClient, NotificationError, NotificationUnavailableError
from simple_logger_handler import LOG_LEVEL, setup_logger
from models import AnimeCreate,AnimeEntry,AnimeList
logger = setup_logger(__name__)
@@ -58,26 +59,10 @@ api = FastAPI(
dependencies=[Depends(auth.authenticate)],
)
register_handlers(api)
user_router = APIRouter(dependencies=[Depends(auth.require(Caller.GATEWAY))])
scheduler_router = APIRouter(dependencies=[Depends(auth.require(Caller.SCHEDULER))])
@api.middleware("http")
async def prometheus_middleware(request: Request, call_next):
logger.debug(f"[Metrics] Incoming request: {request.method} {request.url.path}")
status = 500
try:
response = await call_next(request)
status = response.status_code
logger.debug(f"[Metrics] Request processed with status {status}")
except Exception:
logger.exception("[Metrics] Exception occurred:")
raise
finally:
REQUEST_COUNTER.labels(request.method, request.url.path, status).inc()
logger.debug(f"[Metrics] Counter incremented for {request.method} {request.url.path} [{status}]")
return response
def to_iso(dt: datetime) -> str:
return dt.astimezone(UTC).isoformat(timespec="microseconds")
@@ -175,16 +160,8 @@ def check_seadex(request:Request, db=Depends(get_db)):
@user_router.post("/add/anime")
def add_anime(anime: AnimeCreate, user_id: UserId, db=Depends(get_db)):
logger.info(f"[FastAPI] Received request to track anilist_id={anime.anilist_id}, user_id={user_id}")
try:
anime_name = get_anime_name(anime.anilist_id)
except AnimeNotFoundError as e:
raise HTTPException(status_code=404, detail="Not found on AniList") from e
except MissingAnimeName as e:
raise HTTPException(status_code=404, detail="The anime exists but has no usable title") from e
except AniListError as e:
logger.exception("[FastAPI] AniList request failed")
raise HTTPException(status_code=502, detail="The AniList request failed") from e
anime_name = get_anime_name(anime.anilist_id)
logger.debug(f"[FastAPI] Found name={anime_name} for Anilist id={anime.anilist_id}")
with db.cursor() as cursor: