2026-01-08 13:26:15 -05:00

107 lines
3.7 KiB
Python

"""Web UI Routes."""
import logging
from typing import Optional, Dict, Any
from fastapi import APIRouter, Request
from fastapi.responses import HTMLResponse
import config
import download
from core.cache import series_cache
logger = logging.getLogger("syllabus")
router = APIRouter(tags=["Web UI"])
@router.get("/", include_in_schema=False, response_class=HTMLResponse)
async def index_route(request: Request) -> HTMLResponse:
"""Home page showing list of shows."""
try:
data = series_cache.get()
if data is None:
series_cache.load_from_file(str(config.DROPOUT_JSON))
data = series_cache.get()
if data is None:
return HTMLResponse("<h1>Loading...</h1>", status_code=503)
return request.app.templates.TemplateResponse(
"index.html", {"request": request, "data": data}
)
except Exception as e:
logger.error(f"Error rendering index: {e}")
return HTMLResponse(f"<h1>Error: {str(e)}</h1>", status_code=500)
@router.get("/show/{show}", include_in_schema=False, response_class=HTMLResponse)
async def show_route(request: Request, show: str) -> HTMLResponse:
"""Show page with download options."""
try:
item = await get_show_data(show)
if item:
return request.app.templates.TemplateResponse(
"show.html", {"request": request, "show": item}
)
else:
return HTMLResponse("<h1>Show not found</h1>", status_code=404)
except Exception as e:
logger.error(f"Error rendering show page: {e}")
return HTMLResponse(f"<h1>Error: {str(e)}</h1>", status_code=500)
@router.get("/ydl", include_in_schema=False, response_class=HTMLResponse)
async def ydl_page(request: Request) -> HTMLResponse:
"""YouTube downloader page."""
try:
return request.app.templates.TemplateResponse("ydl.html", {"request": request})
except Exception as e:
logger.error(f"Error rendering YDL page: {e}")
return HTMLResponse(f"<h1>Error: {str(e)}</h1>", status_code=500)
@router.get("/dropout", include_in_schema=False, response_class=HTMLResponse)
async def dropout_page(request: Request) -> HTMLResponse:
"""Dropout downloader page."""
try:
data = series_cache.get()
if data is None:
series_cache.load_from_file(str(config.DROPOUT_JSON))
data = series_cache.get()
if data is None:
return HTMLResponse("<h1>Loading...</h1>", status_code=503)
return request.app.templates.TemplateResponse(
"dropout.html", {"request": request, "data": data}
)
except Exception as e:
logger.error(f"Error rendering dropout page: {e}")
return HTMLResponse(f"<h1>Error: {str(e)}</h1>", status_code=500)
# Helper functions
async def get_show_data(show: str, force: bool = False) -> Optional[Dict[str, Any]]:
"""Get data for a specific show by name or link."""
try:
cached = series_cache.get()
if cached is None:
series_cache.load_from_file(str(config.DROPOUT_JSON))
cached = series_cache.get()
if cached is None:
return None
for item in cached:
if show == item.get("SHOW") or show == item.get("LINK"):
if "SEASONS" not in item or force:
try:
item['SEASONS'] = download.grab.season(item['URL'])
except Exception as e:
logger.error(f"Failed to fetch seasons for {show}: {e}")
item['SEASONS'] = []
return item
return None
except Exception as e:
logger.error(f"Error getting show data: {e}")
return None