from fastapi import APIRouter, Header, HTTPException from app.schemas import ( AuthLogin, AuthRegister, AuthResponse, Destination, FavoriteRequest, FavoriteResponse, ProfileStats, UserProfile, ) from app.services.auth import ( DEMO_TOKEN, get_favorites, get_user_by_token, login_user, register_user, toggle_favorite, ) from app.services.pocketbase import pb router = APIRouter(prefix="/auth", tags=["auth"]) @router.post("/register", response_model=AuthResponse) async def register(body: AuthRegister): result = register_user(body.email, body.password, body.name) if not result: raise HTTPException(400, "该邮箱已注册") return AuthResponse(**result) @router.post("/login", response_model=AuthResponse) async def login(body: AuthLogin): result = login_user(body.email, body.password) if not result: raise HTTPException(401, "邮箱或密码错误") return AuthResponse(**result) @router.get("/me", response_model=UserProfile) async def me(authorization: str | None = Header(None)): token = _extract_token(authorization) user = get_user_by_token(token) if not user: raise HTTPException(401, "未登录") return UserProfile(**user) @router.get("/demo", response_model=AuthResponse) async def demo_login(): """一键体验演示账号""" user = get_user_by_token(DEMO_TOKEN) if not user: raise HTTPException(500, "演示账号不可用") return AuthResponse(token=DEMO_TOKEN, user=UserProfile(**user)) @router.get("/favorites", response_model=FavoriteResponse) async def list_favorites(authorization: str | None = Header(None)): token = _extract_token(authorization) if not get_user_by_token(token): raise HTTPException(401, "未登录") return FavoriteResponse(slugs=get_favorites(token)) @router.get("/favorites/detail", response_model=list[Destination]) async def favorite_details(authorization: str | None = Header(None)): token = _extract_token(authorization) user = get_user_by_token(token) if not user: raise HTTPException(401, "未登录") slugs = get_favorites(token) all_dests = await pb.get_destinations() return [Destination(**d) for d in all_dests if d["slug"] in slugs] @router.get("/profile/stats", response_model=ProfileStats) async def profile_stats(authorization: str | None = Header(None)): token = _extract_token(authorization) user = get_user_by_token(token) if not user: raise HTTPException(401, "未登录") favs = get_favorites(token) levels = [(0, "🌱 新手游民"), (1, "🎒 背包客"), (2, "✈️ 飞行游民"), (3, "🌍 环球游民")] level = levels[min(len(favs), 3)][1] return ProfileStats( favorites_count=len(favs), destinations_explored=len(favs), member_since="2026", nomad_level=level, ) @router.post("/favorites", response_model=FavoriteResponse) async def add_favorite(body: FavoriteRequest, authorization: str | None = Header(None)): token = _extract_token(authorization) if not get_user_by_token(token): raise HTTPException(401, "未登录") dest = await pb.get_destination(body.destination_slug) if not dest: raise HTTPException(404, "目的地不存在") slugs = toggle_favorite(token, body.destination_slug) return FavoriteResponse(slugs=slugs) def _extract_token(authorization: str | None) -> str: if not authorization: return "" if authorization.startswith("Bearer "): return authorization[7:] return authorization