
from flask import request, jsonify
from flask_jwt_extended import jwt_required, get_jwt_identity
from datetime import date, timedelta
from sqlalchemy import desc, func

from . import gamification_bp
from ...models import User, Leaderboard, Achievement, PointActivity
from ...extensions import db
from ...utils.gamification import award_points, is_feature_enabled


@gamification_bp.route('/leaderboards/weekly', methods=['GET'])
def get_weekly_leaderboard():
    """Get current weekly leaderboard"""
    try:
        if not is_feature_enabled('gamification_leaderboards'):
            return jsonify({"error": "Leaderboards disabled"}), 400
        
        # Calculate current week
        today = date.today()
        week_start = today - timedelta(days=today.weekday())
        week_end = week_start + timedelta(days=6)
        
        # Get weekly points by user
        weekly_points = db.session.query(
            PointActivity.user_id,
            func.sum(PointActivity.points_earned).label('total_points'),
            func.count(PointActivity.id).label('activities')
        ).filter(
            PointActivity.created_at >= week_start,
            PointActivity.created_at <= week_end + timedelta(days=1)  # Include full end day
        ).group_by(PointActivity.user_id).order_by(desc('total_points')).limit(50).all()
        
        # Format leaderboard
        leaderboard_data = []
        for rank, (user_id, points, activities) in enumerate(weekly_points, 1):
            user = User.query.get(user_id)
            
            entry_data = {
                "rank": rank,
                "user": {
                    "id": user.id,
                    "name": f"{user.first_name} {user.last_name}",
                    "trade": user.primary_trade,
                    "location": user.location,
                    "level": user.current_level,
                    "league": user.seasonal_league
                },
                "points_earned": int(points),
                "activities_count": activities,
                "jobs_completed": user.jobs_completed,
                "avg_rating": float(user.average_rating) if user.average_rating else 0.0
            }
            leaderboard_data.append(entry_data)
        
        return jsonify({
            "leaderboard": leaderboard_data,
            "period": {
                "type": "weekly",
                "start": week_start.isoformat(),
                "end": week_end.isoformat()
            },
            "total_participants": len(leaderboard_data)
        })
        
    except Exception as e:
        return jsonify({"error": f"Leaderboard fetch failed: {str(e)}"}), 500


@gamification_bp.route('/users/<int:user_id>/achievements', methods=['GET'])
def get_user_achievements(user_id):
    """Get user's achievements and badges"""
    try:
        if not is_feature_enabled('achievement_badges'):
            return jsonify({"error": "Achievement system disabled"}), 400
        
        user = User.query.get_or_404(user_id)
        achievements = Achievement.query.filter_by(user_id=user_id).order_by(
            Achievement.unlocked_at.desc()
        ).all()
        
        achievements_data = []
        for achievement in achievements:
            achievement_data = {
                "id": achievement.id,
                "badge_name": achievement.badge_name,
                "description": achievement.description,
                "points_awarded": achievement.points_awarded,
                "rarity_level": achievement.rarity_level,
                "unlocked_at": achievement.unlocked_at.isoformat(),
                "achievement_type": achievement.achievement_type
            }
            achievements_data.append(achievement_data)
        
        # Calculate stats
        total_achievement_points = sum(a.points_awarded for a in achievements)
        rarity_counts = {}
        for achievement in achievements:
            rarity = achievement.rarity_level
            rarity_counts[rarity] = rarity_counts.get(rarity, 0) + 1
        
        return jsonify({
            "user": {
                "id": user.id,
                "name": f"{user.first_name} {user.last_name}",
                "level": user.current_level,
                "total_points": user.total_points
            },
            "achievements": achievements_data,
            "stats": {
                "total_achievements": len(achievements),
                "points_from_achievements": total_achievement_points,
                "rarity_breakdown": rarity_counts
            }
        })
        
    except Exception as e:
        return jsonify({"error": f"Achievements fetch failed: {str(e)}"}), 500


@gamification_bp.route('/users/<int:user_id>/gamification-stats', methods=['GET'])
def get_gamification_stats(user_id):
    """Get comprehensive gamification statistics"""
    try:
        if not is_feature_enabled('gamification_leaderboards'):
            return jsonify({"error": "Gamification disabled"}), 400
        
        user = User.query.get_or_404(user_id)
        
        # Basic stats
        stats = {
            "user": {
                "id": user.id,
                "name": f"{user.first_name} {user.last_name}",
                "role": user.role,
                "trade": user.primary_trade,
                "level": user.current_level,
                "total_points": user.total_points,
                "seasonal_league": user.seasonal_league
            },
            "level_progress": {
                "current_level": user.current_level,
                "points_for_current_level": (user.current_level - 1) * 500,
                "points_for_next_level": user.current_level * 500,
                "points_to_next_level": max(0, (user.current_level * 500) - user.total_points),
                "progress_percentage": min(100, ((user.total_points % 500) / 500) * 100)
            }
        }
        
        # Recent activities
        recent_activities = PointActivity.query.filter_by(user_id=user_id).order_by(
            PointActivity.created_at.desc()
        ).limit(10).all()
        
        stats["recent_activities"] = [
            {
                "activity_type": activity.activity_type,
                "points_earned": activity.points_earned,
                "description": activity.description,
                "bonus_multiplier": float(activity.bonus_multiplier),
                "bonus_reason": activity.bonus_reason,
                "date": activity.created_at.isoformat()
            }
            for activity in recent_activities
        ]
        
        # Achievement summary
        if is_feature_enabled('achievement_badges'):
            achievements_count = Achievement.query.filter_by(user_id=user_id).count()
            stats["achievements_summary"] = {
                "total_unlocked": achievements_count,
                "points_from_achievements": sum(
                    a.points_awarded for a in Achievement.query.filter_by(user_id=user_id).all()
                )
            }
        
        return jsonify({"gamification_stats": stats})
        
    except Exception as e:
        return jsonify({"error": f"Stats fetch failed: {str(e)}"}), 500
