from datetime import datetime
from flask import jsonify
from sqlalchemy import func
from sqlalchemy.orm import joinedload
from sklearn.cluster import KMeans
import numpy as np
from models import RecentlyWatched, Video  # Assuming these models are already defined in models.py

def analyze_user_activity(user_id):
    try:
        today_date = datetime.now().date()  # Get today's date in YYYY-MM-DD format

        # Total courses completed by the user
        courses_completed = db.session.query(func.count(RecentlyWatched.course_id.distinct())) \
            .filter(RecentlyWatched.user_id == user_id, RecentlyWatched.watched_percentage == 100).scalar() or 0

        # Overall progress (average watched percentage across all activities)
        overall_progress = db.session.query(func.avg(RecentlyWatched.watched_percentage)) \
            .filter(RecentlyWatched.user_id == user_id).scalar() or 0.0

        # Total learning time across all activities
        total_learning_time = db.session.query(func.sum(RecentlyWatched.duration_watched)) \
            .filter(RecentlyWatched.user_id == user_id).scalar() or 0

        # Learning time spent today
        today_learning_time = db.session.query(func.sum(RecentlyWatched.duration_watched)) \
            .filter(RecentlyWatched.user_id == user_id, func.date(RecentlyWatched.time_watched) == today_date).scalar() or 0

        # Fetch raw activity data for deeper analysis
        activity_data = db.session.query(
            RecentlyWatched.duration_watched, RecentlyWatched.watched_percentage, RecentlyWatched.time_watched
        ).filter(RecentlyWatched.user_id == user_id).all()

        # ML Analysis: Activity Clustering
        cluster_analysis = {}
        if activity_data:
            activity_array = np.array([[row.duration_watched, row.watched_percentage] for row in activity_data])
            kmeans = KMeans(n_clusters=3, random_state=42).fit(activity_array)
            cluster_labels = kmeans.labels_

            cluster_analysis = {
                "cluster_0_count": np.sum(cluster_labels == 0),
                "cluster_1_count": np.sum(cluster_labels == 1),
                "cluster_2_count": np.sum(cluster_labels == 2),
                "centroids": kmeans.cluster_centers_.tolist(),
            }
        else:
            cluster_analysis = {"message": "No activity data available for clustering."}

        # Trend Analysis: Learning time over last 7 days
        weekly_data = db.session.query(
            func.date(RecentlyWatched.time_watched).label('date'),
            func.sum(RecentlyWatched.duration_watched).label('daily_time')
        ).filter(RecentlyWatched.user_id == user_id,
                 RecentlyWatched.time_watched >= datetime.now() - timedelta(days=7)) \
            .group_by(func.date(RecentlyWatched.time_watched)).all()

        learning_trends = {row.date: row.daily_time for row in weekly_data} if weekly_data else {}

        # Engagement Score (weighted average of key metrics)
        engagement_score = round(
            (0.5 * overall_progress) +
            (0.3 * (total_learning_time / (60 * 60))) +  # Convert total time to hours
            (0.2 * len(activity_data)), 2
        ) if activity_data else 0

        # Final analysis result
        analysis_result = {
            "courses_completed": courses_completed,
            "overall_progress": round(overall_progress, 2),
            "total_learning_time": total_learning_time,
            "today_learning_time": today_learning_time,
            "learning_trends": learning_trends,
            "cluster_analysis": cluster_analysis,
            "engagement_score": engagement_score
        }

        return analysis_result

    except Exception as e:
        return {"error": str(e)}
