from fastapi import APIRouter, Depends, HTTPException
from motor.motor_asyncio import AsyncIOMotorDatabase
from app.api import deps
from app.db.session import get_db
from app.models.schemas import User, GameScore, LeaderboardEntry
from typing import List
import uuid
import random

router = APIRouter()

@router.get("", response_model=List[dict])
async def get_games():
    games = [
        {
            "id": "otp-fraud",
            "name": "OTP Fraud Awareness",
            "description": "Learn to identify and prevent OTP fraud attempts",
            "category": "fraud-prevention",
            "difficulty": "beginner",
            "estimated_time": 5,
            "thumbnail": "/api/placeholder/400/250"
        },
        {
            "id": "phishing-detection",
            "name": "Phishing Email Detective",
            "description": "Spot phishing emails before they fool you",
            "category": "email-security",
            "difficulty": "intermediate",
            "estimated_time": 8,
            "thumbnail": "/api/placeholder/400/250"
        },
        {
            "id": "social-media-doxing",
            "name": "Social Media Privacy Guard",
            "description": "Protect yourself from doxing and information gathering",
            "category": "privacy-protection",
            "difficulty": "advanced",
            "estimated_time": 10,
            "thumbnail": "/api/placeholder/400/250"
        }
    ]
    return games

@router.post("/score", response_model=GameScore)
async def submit_game_score(
    *,
    db: AsyncIOMotorDatabase = Depends(get_db),
    score_data: GameScore,
    current_user: User = Depends(deps.get_current_user)
):
    score_data.user_id = current_user.id
    
    points_earned = score_data.score * 10
    if score_data.completed:
        points_earned += 100
    
    await db.users.update_one(
        {"id": current_user.id},
        {
            "$inc": {"total_points": points_earned},
            "$addToSet": {"games_completed": score_data.game_name}
        }
    )
    
    await db.game_scores.insert_one(score_data.dict())
    await check_and_award_badges(db, current_user.id)
    
    return score_data

async def check_and_award_badges(db: AsyncIOMotorDatabase, user_id: str):
    user = await db.users.find_one({"id": user_id})
    if not user:
        return
    
    new_badges = []
    games_completed = user.get("games_completed", [])
    badges = user.get("badges", [])
    total_points = user.get("total_points", 0)
    
    if len(games_completed) >= 1 and "first-game" not in badges:
        new_badges.append("first-game")
    
    if len(games_completed) >= 3 and "game-master" not in badges:
        new_badges.append("game-master")
    
    if total_points >= 1000 and "points-1000" not in badges:
        new_badges.append("points-1000")
    
    if new_badges:
        await db.users.update_one(
            {"id": user_id},
            {"$addToSet": {"badges": {"$each": new_badges}}}
        )

@router.get("/leaderboard", response_model=List[LeaderboardEntry])
async def get_leaderboard(
    *,
    db: AsyncIOMotorDatabase = Depends(get_db),
    timeframe: str = "all-time",
    category: str = "overall",
    limit: int = 50
):
    pipeline = [
        {
            "$project": {
                "user_id": "$id",
                "username": 1,
                "total_points": 1,
                "games_completed": {"$size": {"$ifNull": ["$games_completed", []]}},
                "badges_count": {"$size": {"$ifNull": ["$badges", []]}}
            }
        },
        {"$sort": {"total_points": -1}},
        {"$limit": limit}
    ]
    
    leaderboard = await db.users.aggregate(pipeline).to_list(length=limit)
    
    if timeframe != "all-time" or category != "overall":
        results = []
        for user in leaderboard:
            modified_user = user.copy()
            if timeframe == "weekly":
                modified_user["total_points"] = int(user["total_points"] * 0.1)
            elif timeframe == "monthly":
                modified_user["total_points"] = int(user["total_points"] * 0.4)
                
            if category == "games":
                modified_user["total_points"] = user["games_completed"] * 100
            elif category == "badges":
                modified_user["total_points"] = user["badges_count"] * 50
                
            results.append(modified_user)
        results.sort(key=lambda x: x["total_points"], reverse=True)
        leaderboard = results

    return leaderboard

@router.get("/badges", response_model=List[dict])
async def get_available_badges():
    return [
        {"id": "first-game", "name": "First Steps", "description": "Complete your first cybercrime awareness game", "icon": "🎯", "category": "achievement"},
        {"id": "game-master", "name": "Game Master", "description": "Complete 3 different cybercrime awareness games", "icon": "🏆", "category": "achievement"},
        {"id": "points-1000", "name": "Point Collector", "description": "Earn 1000+ points", "icon": "💎", "category": "milestone"},
        {"id": "cyber-guardian", "name": "Cyber Guardian", "description": "Perfect score on all beginner games", "icon": "🛡️", "category": "mastery"}
    ]
