from __future__ import annotations from fastapi import APIRouter, Depends, Header, HTTPException, Query, Request from fastapi.responses import HTMLResponse from app.services.app_services import AppServices def get_router() -> APIRouter: router = APIRouter() def runtime(request: Request): return request.app.state.runtime def services(request: Request) -> AppServices: return request.app.state.services @router.get("/health") async def health(): return {"ok": True} @router.get("/auth/spotify/start") async def spotify_start( chat_id: str = Query(...), username: str | None = Query(default=None), svc: AppServices = Depends(services), ): url = await svc.auth.create_connect_url(chat_id=chat_id, username=username) return {"url": url} @router.get("/auth/spotify/callback", response_class=HTMLResponse) async def spotify_callback( request: Request, code: str | None = None, state: str | None = None, error: str | None = None, svc: AppServices = Depends(services), ): try: if error: raise ValueError(f"Spotify returned error: {error}") if not code or not state: raise ValueError("Missing code/state in callback") chat_id, display_name = await svc.auth.handle_callback(code=code, state=state) runner = request.app.state.runtime.telegram_runner if runner is not None: await runner.send_spotify_connected_notice(chat_id, display_name) return """

Spotify connected

Return to Telegram and use /generate.

""" except Exception as exc: return HTMLResponse( content=( "" f"

Auth failed

{exc}

" ), status_code=400, ) @router.post("/internal/jobs/nightly") async def run_nightly( request: Request, authorization: str | None = Header(default=None), svc: AppServices = Depends(services), ): rt = runtime(request) expected = f"Bearer {rt.settings.internal_job_token}" if authorization != expected: raise HTTPException(status_code=401, detail="Unauthorized") outcomes = await svc.jobs.generate_for_all_connected_users() return { "ok": True, "count": len(outcomes), "results": [ {"user_id": o.user_id, "ok": o.ok, "message": o.message, "playlist_url": o.playlist_url} for o in outcomes ], } return router