from flask import Blueprint, render_template, request, redirect, url_for, flash, jsonify
from flask_login import login_required, current_user
from app.extensions import db
from app.models import User, Course, Trainer, TrainerTicket, TrainerTicketMessage
from app.models.features import Notification
from functools import wraps

tickets_bp = Blueprint("tickets", __name__, url_prefix="/tickets")


def premium_required(f):
    """Decorator to require premium subscription for route access."""
    @wraps(f)
    @login_required
    def decorated(*args, **kwargs):
        if not current_user.has_premium_access:
            flash("هذه الميزة متاحة فقط للمشتركين في الخطط المدفوعة", "warning")
            return redirect(url_for('subscription.plans'))
        return f(*args, **kwargs)
    return decorated


def send_ticket_notification(ticket, message_content, recipient_id):
    """Send notification for new ticket or message."""
    try:
        if message_content:
            # This is a reply notification
            title = "رد جديد على تذكرتك"
            message = message_content[:100] + "..." if len(message_content) > 100 else message_content
        else:
            # This is a new ticket notification
            if ticket.ticket_type == "help":
                title = "طلب مساعدة جديد"
                message = f"طلب مساعدة جديد في الدورة: {ticket.course.title_ar}"
            else:  # apply
                title = "طلب تقديم جديد"
                message = f"طلب تقديم جديد للدورة: {ticket.course.title_ar}"

        notification = Notification(
            user_id=recipient_id,
            title=title,
            message=message,
            category="ticket",
            link=url_for("tickets.detail", ticket_id=ticket.id)
        )
        db.session.add(notification)
        db.session.commit()
    except Exception as e:
        print(f"Notification error: {e}")


@tickets_bp.route("/my-tickets")
@premium_required
def my_tickets():
    """View my tickets (as student or trainer)."""
    if current_user.role == "admin":
        # Admins see all tickets
        tickets = TrainerTicket.query.order_by(TrainerTicket.created_at.desc()).all()
    elif current_user.role == "trainer":
        # Trainers see tickets assigned to them
        tickets = TrainerTicket.query.filter_by(trainer_id=current_user.id).order_by(
            TrainerTicket.created_at.desc()).all()
    else:
        # Students see their own tickets
        tickets = TrainerTicket.query.filter_by(student_id=current_user.id).order_by(
            TrainerTicket.created_at.desc()).all()

    return render_template("tickets/my_tickets.html", tickets=tickets)


@tickets_bp.route("/new/<int:course_id>/<ticket_type>")
@login_required
def new_ticket(course_id, ticket_type):
    """Create new ticket form."""
    if ticket_type not in ["help", "apply"]:
        flash("نوع التذكرة غير صحيح", "error")
        return redirect(url_for("courses.index"))

    course = Course.query.get_or_404(course_id)

    # Trainer model doesn't have user_id, so tickets go to admin
    trainer_user_id = None

    return render_template("tickets/new_ticket.html",
                         course=course,
                         ticket_type=ticket_type,
                         trainer_user_id=trainer_user_id)


@tickets_bp.route("/create/<int:course_id>", methods=["POST"])
@login_required
def create_ticket(course_id):
    """Create a new ticket."""
    course = Course.query.get_or_404(course_id)
    ticket_type = request.form.get("ticket_type")
    subject = request.form.get("subject")
    message = request.form.get("message")

    if ticket_type not in ["help", "apply"]:
        return jsonify({"error": "Invalid ticket type"}), 400

    if not subject or not message:
        return jsonify({"error": "Subject and message are required"}), 400

    # Get application-specific fields for "apply" type
    application_budget = request.form.get("application_budget")
    application_city = request.form.get("application_city")
    application_timeline = request.form.get("application_timeline")
    application_team_size = request.form.get("application_team_size")

    # Find trainer user ID - Trainer model doesn't have user_id linked to User
    # Tickets go to admin by default
    trainer_user_id = None

    if not trainer_user_id:
        # Get first admin user
        admin = User.query.filter_by(role="admin").first()
        if admin:
            trainer_user_id = admin.id
        else:
            return jsonify({"error": "No trainer or admin available"}), 400

    # Create ticket
    ticket = TrainerTicket(
        course_id=course.id,
        student_id=current_user.id,
        trainer_id=trainer_user_id,
        ticket_type=ticket_type,
        subject=subject,
        application_budget=float(application_budget) if application_budget else None,
        application_city=application_city if application_city else None,
        application_timeline=application_timeline if application_timeline else None,
        application_team_size=int(application_team_size) if application_team_size else None
    )
    db.session.add(ticket)
    db.session.flush()

    # Add initial message
    msg = TrainerTicketMessage(
        ticket_id=ticket.id,
        sender_id=current_user.id,
        message=message
    )
    db.session.add(msg)
    db.session.commit()

    # Send notification to trainer
    send_ticket_notification(ticket, message, trainer_user_id)

    return jsonify({"success": True, "ticket_id": ticket.id})


@tickets_bp.route("/<int:ticket_id>")
@login_required
def detail(ticket_id):
    """View ticket details and chat."""
    ticket = TrainerTicket.query.get_or_404(ticket_id)

    # Check permissions
    if current_user.role != "admin":
        if current_user.role == "trainer":
            if ticket.trainer_id != current_user.id:
                flash("ليس لديك صلاحية لعرض هذه التذكرة", "error")
                return redirect(url_for("tickets.my_tickets"))
        else:  # student
            if ticket.student_id != current_user.id:
                flash("ليس لديك صلاحية لعرض هذه التذكرة", "error")
                return redirect(url_for("tickets.my_tickets"))

    # Mark messages as read
    if current_user.role == "trainer":
        unread_messages = ticket.messages.filter_by(is_read=False).filter(
            TrainerTicketMessage.sender_id != current_user.id).all()
    else:
        unread_messages = ticket.messages.filter_by(is_read=False).filter(
            TrainerTicketMessage.sender_id != current_user.id).all()

    for msg in unread_messages:
        msg.is_read = True
    db.session.commit()

    return render_template("tickets/detail.html", ticket=ticket)


@tickets_bp.route("/<int:ticket_id>/message", methods=["POST"])
@login_required
def send_message(ticket_id):
    """Send a message in a ticket."""
    ticket = TrainerTicket.query.get_or_404(ticket_id)

    # Check permissions
    if current_user.role == "student":
        if ticket.student_id != current_user.id:
            return jsonify({"error": "Unauthorized"}), 403
    elif current_user.role == "trainer":
        if ticket.trainer_id != current_user.id:
            return jsonify({"error": "Unauthorized"}), 403
    elif current_user.role != "admin":
        return jsonify({"error": "Unauthorized"}), 403

    message = request.form.get("message")
    if not message:
        return jsonify({"error": "Message is required"}), 400

    # Create message
    msg = TrainerTicketMessage(
        ticket_id=ticket.id,
        sender_id=current_user.id,
        message=message
    )
    db.session.add(msg)

    # Update ticket status
    if ticket.status == "open":
        ticket.status = "in_progress"

    db.session.commit()

    # Send notification
    if current_user.role == "student":
        recipient_id = ticket.trainer_id
    else:
        recipient_id = ticket.student_id

    send_ticket_notification(ticket, message, recipient_id)

    return jsonify({
        "success": True,
        "message_id": msg.id,
        "created_at": msg.created_at.strftime("%Y-%m-%d %H:%M")
    })


@tickets_bp.route("/<int:ticket_id>/close", methods=["POST"])
@login_required
def close_ticket(ticket_id):
    """Close a ticket."""
    ticket = TrainerTicket.query.get_or_404(ticket_id)

    # Check permissions
    if current_user.role not in ["admin", "trainer"]:
        if ticket.student_id != current_user.id:
            return jsonify({"error": "Unauthorized"}), 403

    ticket.status = "closed"
    db.session.commit()

    return jsonify({"success": True})


@tickets_bp.route("/<int:ticket_id>/reopen", methods=["POST"])
@login_required
def reopen_ticket(ticket_id):
    """Reopen a closed ticket."""
    ticket = TrainerTicket.query.get_or_404(ticket_id)

    # Check permissions
    if current_user.role not in ["admin", "trainer"]:
        if ticket.student_id != current_user.id:
            return jsonify({"error": "Unauthorized"}), 403

    ticket.status = "open"
    db.session.commit()

    return jsonify({"success": True})


@tickets_bp.route("/api/<int:ticket_id>/messages")
@login_required
def api_messages(ticket_id):
    """API endpoint for polling new messages."""
    ticket = TrainerTicket.query.get_or_404(ticket_id)

    # Check permissions
    if current_user.role == "student":
        if ticket.student_id != current_user.id:
            return jsonify({"error": "Unauthorized"}), 403
    elif current_user.role == "trainer":
        if ticket.trainer_id != current_user.id:
            return jsonify({"error": "Unauthorized"}), 403

    last_id = request.args.get("last_id", 0, type=int)
    messages = ticket.messages.filter(TrainerTicketMessage.id > last_id).order_by(
        TrainerTicketMessage.created_at).all()

    return jsonify({
        "messages": [
            {
                "id": m.id,
                "sender_id": m.sender_id,
                "sender_name": m.sender.name,
                "message": m.message,
                "is_from_student": m.is_from_student,
                "created_at": m.created_at.strftime("%Y-%m-%d %H:%M")
            }
            for m in messages
        ]
    })
