from flask.views import MethodView
from flask_smorest import Blueprint
from src.views.teaching_session.utils import TeachingSessionManager
from flask import request
from src.views.teaching_session.continuous_sessions import continuous_session_manager

session_router = Blueprint("Teaching Session Routes", __name__, description="Operations on teaching sessions")


# Initialize continuous session monitoring
@session_router.before_app_request
def initialize_session_monitoring():
    """Initialize continuous session monitoring on app startup"""
    continuous_session_manager.start_monitoring()

@session_router.route("/sessions")
class TeachingSessionListRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self):
        """
        Get teaching sessions with optional filters
        - Can filter by tutor_id, course_id, student_id, or supervisor_id
        - Date range filtering available
        """
        tutor_id = request.args.get('tutor_id', type=str)
        course_id = request.args.get('course_id', type=str)
        student_id = request.args.get('student_id', type=str)
        supervisor_id = request.args.get('supervisor_id', type=str)
        start_date = request.args.get('start_date', type=str)
        end_date = request.args.get('end_date', type=str)
        status = request.args.get('status', type=str)
        
        if tutor_id:
            return self.session_manager.get_sessions_for_tutor(tutor_id, start_date, end_date)
        elif course_id:
            return self.session_manager.get_sessions_for_course(course_id, start_date, end_date)
        elif student_id:
            return self.session_manager.get_sessions_for_student(student_id, start_date, end_date)
        elif supervisor_id:
            return self.session_manager.get_sessions_for_supervisor(supervisor_id, start_date, end_date, status)
        else:
            return {"message": "Must provide one of: tutor_id, course_id, student_id, or supervisor_id"}, 400

    def post(self):
        """Create a new teaching session"""
        payload = request.get_json()
        return self.session_manager.create(payload)

@session_router.route("/sessions/<string:session_id>")
class TeachingSessionDetailRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, session_id):
        """Get session details"""
        return self.session_manager.get(session_id)

    def put(self, session_id):
        """Update session details"""
        payload = request.get_json()
        return self.session_manager.update(session_id, payload)

    def delete(self, session_id):
        """Delete a session"""
        return self.session_manager.delete(session_id)

@session_router.route("/sessions/<string:session_id>/checkin")
class TeachingSessionCheckInRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Check in a tutor for a session"""
        payload = request.get_json()
        return self.session_manager.check_in_tutor(session_id, payload)

@session_router.route("/sessions/<string:session_id>/checkout")
class TeachingSessionCheckOutRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Check out a tutor from a session"""
        payload = request.get_json()
        return self.session_manager.check_out_tutor(session_id, payload)

@session_router.route("/sessions/<string:session_id>/verify")
class TeachingSessionVerifyRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Verify a completed session by supervisor"""
        supervisor_id = request.args.get('supervisor_id', type=str)
        if not supervisor_id:
            return {"message": "supervisor_id parameter is required"}, 400
            
        payload = request.get_json()
        return self.session_manager.verify_session(session_id, supervisor_id, payload)

@session_router.route("/sessions/<string:session_id>/attendance")
class TeachingSessionAttendanceRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, session_id):
        """Get attendance records for a session"""
        return self.session_manager.get_attendance_for_session(session_id)

    def post(self, session_id):
        """Record attendance for a session"""
        payload = request.get_json()
        return self.session_manager.record_attendance(session_id, payload)

@session_router.route("/students/<string:student_id>/attendance")
class StudentAttendanceRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, student_id):
        """Get attendance records for a student"""
        course_id = request.args.get('course_id', type=str)
        return self.session_manager.get_attendance_for_student(student_id, course_id)

@session_router.route("/courses/<string:course_id>/attendance-report")
class AttendanceReportRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, course_id):
        """Generate an attendance report for a course"""
        start_date = request.args.get('start_date', type=str)
        end_date = request.args.get('end_date', type=str)
        return self.session_manager.generate_attendance_report(course_id, start_date, end_date)

@session_router.route("/tutors/<string:tutor_id>/teaching-report")
class TeachingReportRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, tutor_id):
        """Generate a teaching report for a tutor"""
        start_date = request.args.get('start_date', type=str)
        end_date = request.args.get('end_date', type=str)
        return self.session_manager.generate_tutor_teaching_report(tutor_id, start_date, end_date)

@session_router.route("/sessions/<string:session_id>/start")
class TeachingSessionStartRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Start a teaching session"""
        tutor_id = request.args.get('tutor_id', type=str)
        if not tutor_id:
            return {"message": "tutor_id parameter is required"}, 400
        return self.session_manager.start_session(session_id, tutor_id)

@session_router.route("/sessions/<string:session_id>/end")
class TeachingSessionEndRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """End a teaching session"""
        tutor_id = request.args.get('tutor_id', type=str)
        if not tutor_id:
            return {"message": "tutor_id parameter is required"}, 400
        return self.session_manager.end_session(session_id, tutor_id)

@session_router.route("/sessions/<string:session_id>/attendees")
class TeachingSessionAttendeesRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, session_id):
        """Get attendees for a teaching session"""
        tutor_id = request.args.get('tutor_id', type=str)
        if not tutor_id:
            return {"message": "tutor_id parameter is required"}, 400
        return self.session_manager.get_session_attendees(session_id, tutor_id)

@session_router.route("/sessions/<string:session_id>/record-attendance")
class TeachingSessionRecordAttendanceRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Record attendance for a student in a session"""
        payload = request.get_json()
        tutor_id = request.args.get('tutor_id', type=str)
        if not tutor_id:
            return {"message": "tutor_id parameter is required"}, 400
        
        student_id = payload.get('student_id')
        status = payload.get('status')
        notes = payload.get('notes')
        
        if not student_id or not status:
            return {"message": "student_id and status are required"}, 400
            
        return self.session_manager.record_student_attendance(session_id, student_id, tutor_id, status, notes)

@session_router.route("/sessions/<string:session_id>/bulk-attendance")
class TeachingSessionBulkAttendanceRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Record attendance for multiple students in a session"""
        payload = request.get_json()
        tutor_id = request.args.get('tutor_id', type=str)
        if not tutor_id:
            return {"message": "tutor_id parameter is required"}, 400
        
        attendance_data = payload.get('attendance_data', [])
        if not attendance_data:
            return {"message": "attendance_data is required"}, 400
            
        return self.session_manager.record_bulk_attendance(session_id, tutor_id, attendance_data)

@session_router.route("/sessions/<string:session_id>/ongoing-attendance")
class TeachingSessionOngoingAttendanceRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, session_id):
        """Get attendance information for an ongoing session"""
        tutor_id = request.args.get('tutor_id', type=str)
        if not tutor_id:
            return {"message": "tutor_id parameter is required"}, 400
        
        return self.session_manager.get_ongoing_session_attendance(session_id, tutor_id)

@session_router.route("/sessions/monitoring/start")
class TeachingSessionMonitoringStartRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self):
        """Start continuous session monitoring"""
        return self.session_manager.start_continuous_monitoring()

@session_router.route("/sessions/monitoring/stop")
class TeachingSessionMonitoringStopRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self):
        """Stop continuous session monitoring"""
        return self.session_manager.stop_continuous_monitoring()

# Makeup Session Routes
@session_router.route("/makeup-sessions")
class MakeupSessionListRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self):
        """
        Get makeup sessions with optional filters
        - Can filter by tutor_id, course_id, status
        - Date range filtering available
        """
        tutor_id = request.args.get('tutor_id', type=str)
        course_id = request.args.get('course_id', type=str)
        status = request.args.get('status', type=str)
        start_date = request.args.get('start_date', type=str)
        end_date = request.args.get('end_date', type=str)
        
        if tutor_id:
            return self.session_manager.get_makeup_sessions_for_tutor(tutor_id, start_date, end_date, status)
        elif course_id:
            return self.session_manager.get_makeup_sessions_for_course(course_id, start_date, end_date, status)
        else:
            return {"message": "Must provide tutor_id or course_id"}, 400

    def post(self):
        """Create a new makeup session"""
        payload = request.get_json()
        return self.session_manager.create_makeup_session(payload)

@session_router.route("/makeup-sessions/<string:session_id>")
class MakeupSessionDetailRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, session_id):
        """Get makeup session details"""
        return self.session_manager.get_makeup_session(session_id)

    def put(self, session_id):
        """Update makeup session details"""
        payload = request.get_json()
        return self.session_manager.update_makeup_session(session_id, payload)

    def delete(self, session_id):
        """Delete a makeup session"""
        return self.session_manager.delete_makeup_session(session_id)

@session_router.route("/makeup-sessions/<string:session_id>/cancel")
class MakeupSessionCancelRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def patch(self, session_id):
        """Cancel a makeup session"""
        return self.session_manager.cancel_makeup_session(session_id)

@session_router.route("/makeup-sessions/<string:session_id>/send-reminders")
class MakeupSessionRemindersRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Send reminders for a makeup session"""
        payload = request.get_json()
        requester_id = payload.get('requester_id')
        requester_type = payload.get('requester_type', 'tutor')
        
        if not requester_id:
            return {"message": "requester_id is required"}, 400
            
        return self.session_manager.send_makeup_session_reminders(session_id, requester_id, requester_type)

@session_router.route("/makeup-sessions/send-bulk-reminders")
class MakeupSessionBulkRemindersRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self):
        """Send bulk reminders for multiple makeup sessions"""
        payload = request.get_json()
        session_ids = payload.get('session_ids', [])
        requester_id = payload.get('requester_id')
        requester_type = payload.get('requester_type', 'tutor')
        
        if not session_ids or not requester_id:
            return {"message": "session_ids and requester_id are required"}, 400
            
        return self.session_manager.send_bulk_makeup_session_reminders(session_ids, requester_id, requester_type)

# Daily Teaching Sessions Routes
@session_router.route("/daily-teaching-sessions")
class DailyTeachingSessionListRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self):
        """
        Get daily teaching sessions with optional filters
        - Can filter by user_id, tutor_id, course_id, teaching_session_id, status
        - Date range filtering available
        """
        user_id = request.args.get('user_id', type=str)
        tutor_id = request.args.get('tutor_id', type=str)
        course_id = request.args.get('course_id', type=str)
        teaching_session_id = request.args.get('teaching_session_id', type=str)
        status = request.args.get('status', type=str)
        start_date = request.args.get('start_date', type=str)
        end_date = request.args.get('end_date', type=str)
        include_course = request.args.get('include_course', 'false').lower() == 'true'
        include_tutor = request.args.get('include_tutor', 'false').lower() == 'true'
        
        if user_id:
            return self.session_manager.get_daily_sessions_for_user(user_id, start_date, end_date, status, include_course, include_tutor)
        elif tutor_id:
            return self.session_manager.get_daily_sessions_for_tutor(tutor_id, start_date, end_date, status, include_course, include_tutor)
        elif course_id:
            return self.session_manager.get_daily_sessions_for_course(course_id, start_date, end_date, status, include_course, include_tutor)
        elif teaching_session_id:
            return self.session_manager.get_daily_sessions_for_teaching_session(teaching_session_id, start_date, end_date, status, include_course, include_tutor)
        else:
            return {"message": "Must provide user_id, tutor_id, course_id, or teaching_session_id"}, 400

    def post(self):
        """Create a new daily teaching session"""
        payload = request.get_json()
        return self.session_manager.create_daily_session(payload)

@session_router.route("/daily-teaching-sessions/<string:session_id>")
class DailyTeachingSessionDetailRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def get(self, session_id):
        """Get daily teaching session details"""
        return self.session_manager.get_daily_session(session_id)

    def put(self, session_id):
        """Update daily teaching session details"""
        payload = request.get_json()
        return self.session_manager.update_daily_session(session_id, payload)

    def delete(self, session_id):
        """Delete a daily teaching session"""
        return self.session_manager.delete_daily_session(session_id)

@session_router.route("/daily-teaching-sessions/<string:session_id>/start")
class DailyTeachingSessionStartRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Start a daily teaching session with automatic tutor attendance recording"""
        payload = request.get_json()
        return self.session_manager.start_daily_session(session_id, payload)

@session_router.route("/daily-teaching-sessions/<string:session_id>/end")
class DailyTeachingSessionEndRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """End a daily teaching session"""
        return self.session_manager.end_daily_session(session_id)

@session_router.route("/daily-teaching-sessions/<string:session_id>/send-reminder")
class DailyTeachingSessionReminderRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Send reminder emails to all students in the class"""
        payload = request.get_json()
        return self.session_manager.send_daily_session_reminder(session_id, payload)

@session_router.route("/daily-teaching-sessions/<string:session_id>/tutor-attendance")
class DailyTeachingSessionTutorAttendanceRouter(MethodView):
    def __init__(self) -> None:
        self.session_manager = TeachingSessionManager()

    def post(self, session_id):
        """Record tutor attendance for a daily session"""
        payload = request.get_json()
        return self.session_manager.record_tutor_attendance(session_id, payload)