import random
import string
import logging
from django.core.mail import EmailMultiAlternatives
from django.template.loader import render_to_string
from django.utils.html import strip_tags
from django.conf import settings
from django.db.models import Count

logger = logging.getLogger(__name__)

def generate_otp(length=6):
    """Génère un code numérique aléatoire de 6 chiffres."""
    return ''.join(random.choices(string.digits, k=length))

def send_otp_email(email, otp_code):
    """Envoie le code OTP et le lien d'activation par email (lien + code valables 24h, usage unique)."""
    subject = 'Votre code d\'activation GOON'
    frontend_url = settings.FRONTEND_URL.rstrip('/')
    activate_link = f"{frontend_url}/activate?email={email}&token={otp_code}"
    context = {
        'otp_code': otp_code,
        'email': email,
        'activate_link': activate_link,
    }
    html_content = render_to_string('emails/invite_email.html', context)
    text_content = strip_tags(html_content)
    email_from = settings.EMAIL_HOST_USER
    try:
        msg = EmailMultiAlternatives(subject, text_content, email_from, [email])
        msg.attach_alternative(html_content, "text/html")
        msg.send()
        logger.info("Activation email sent to %s", email)
        return True
    except Exception:
        logger.exception("Erreur envoi email activation vers %s", email)
        return False


def send_register_pending_email(email, first_name):
    """Après inscription : expliquer que le compte est en attente de validation par l'admin."""
    context = {'email': email, 'first_name': first_name or 'Utilisateur'}
    subject = 'GOON – Votre inscription a bien été enregistrée'
    html_content = render_to_string('emails/register_pending.html', context)
    text_content = strip_tags(html_content)
    try:
        msg = EmailMultiAlternatives(subject, text_content, settings.EMAIL_HOST_USER, [email])
        msg.attach_alternative(html_content, "text/html")
        msg.send()
        logger.info("Register pending email sent to %s", email)
        return True
    except Exception:
        logger.exception("Erreur envoi email inscription pending vers %s", email)
        return False


def send_account_activated_email(email, first_name):
    """Quand l'admin active le compte : notifier l'utilisateur qu'il peut se connecter."""
    frontend_url = settings.FRONTEND_URL.rstrip('/')
    context = {'email': email, 'first_name': first_name or 'Utilisateur', 'frontend_url': frontend_url}
    subject = 'GOON – Votre compte est activé'
    html_content = render_to_string('emails/account_activated.html', context)
    text_content = strip_tags(html_content)
    try:
        msg = EmailMultiAlternatives(subject, text_content, settings.EMAIL_HOST_USER, [email])
        msg.attach_alternative(html_content, "text/html")
        msg.send()
        logger.info("Account activated email sent to %s", email)
        return True
    except Exception:
        logger.exception("Erreur envoi email compte activé vers %s", email)
        return False


def send_password_reset_email(email, otp_code):
    """Mot de passe oublié : envoie le code et le lien de réinitialisation (24h)."""
    frontend_url = settings.FRONTEND_URL.rstrip('/')
    reset_link = f"{frontend_url}/reset-password?email={email}&token={otp_code}"
    context = {'otp_code': otp_code, 'email': email, 'reset_link': reset_link}
    subject = 'GOON – Réinitialisation de votre mot de passe'
    html_content = render_to_string('emails/password_reset.html', context)
    text_content = strip_tags(html_content)
    try:
        msg = EmailMultiAlternatives(subject, text_content, settings.EMAIL_HOST_USER, [email])
        msg.attach_alternative(html_content, "text/html")
        msg.send()
        logger.info("Password reset email sent to %s", email)
        return True
    except Exception:
        logger.exception("[GOON] Erreur envoi email reset password vers %s", email)
        return False


# --- Mentor (Option C) ---
def get_mentor_to_assign():
    """
    Retourne un mentor à assigner (celui qui a le moins d'étudiants).
    Retourne None s'il n'y a aucun utilisateur avec role=MENTOR.
    """
    from django.contrib.auth import get_user_model
    User = get_user_model()
    mentors = User.objects.filter(role=User.Role.MENTOR, is_active=True).annotate(
        n_students=Count('mentored_students')
    ).order_by('n_students')
    return mentors.first()


def send_mentor_changed_to_student_email(student_email, student_first_name, new_mentor_name):
    """Quand l'admin change le mentor : notifier l'étudiant (nouveau mentor)."""
    context = {
        'first_name': student_first_name or 'Utilisateur',
        'mentor_name': new_mentor_name or 'votre mentor',
    }
    subject = 'GOON – Un nouveau mentor vous a été assigné'
    html_content = render_to_string('emails/mentor_changed_student.html', context)
    text_content = strip_tags(html_content)
    try:
        msg = EmailMultiAlternatives(subject, text_content, settings.EMAIL_HOST_USER, [student_email])
        msg.attach_alternative(html_content, "text/html")
        msg.send()
        logger.info(
            "[GOON] Email changement mentor envoyé à l'étudiant %s (mentor %s)",
            student_email,
            new_mentor_name,
        )
        return True
    except Exception:
        logger.exception(
            "[GOON] Erreur envoi email changement mentor (étudiant) vers %s",
            student_email,
        )
        return False


def send_new_student_assigned_to_mentor_email(mentor_email, mentor_first_name, student_name):
    """Quand l'admin assigne un nouvel étudiant au mentor : notifier le mentor."""
    frontend_url = settings.FRONTEND_URL.rstrip('/')
    context = {
        'first_name': mentor_first_name or 'Mentor',
        'student_name': student_name or 'un étudiant',
        'frontend_url': frontend_url,
    }
    subject = 'GOON – Un nouvel étudiant vous a été assigné'
    html_content = render_to_string('emails/mentor_new_student.html', context)
    text_content = strip_tags(html_content)
    try:
        msg = EmailMultiAlternatives(subject, text_content, settings.EMAIL_HOST_USER, [mentor_email])
        msg.attach_alternative(html_content, "text/html")
        msg.send()
        logger.info(
            "[GOON] Email nouvel étudiant envoyé au mentor %s (étudiant %s)",
            mentor_email,
            student_name,
        )
        return True
    except Exception:
        logger.exception(
            "[GOON] Erreur envoi email nouvel étudiant (mentor) vers %s",
            mentor_email,
        )
        return False