from django.contrib.auth.views import LoginView as BaseLoginView, LogoutView as BaseLogoutView, \
    PasswordResetView as BasePasswordResetView, PasswordResetConfirmView as BasePasswordResetConfirmView
from django.db.models.query_utils import Q
from django.urls.base import reverse_lazy
from django.utils.translation import ugettext as _
from django.views.generic.base import TemplateView, ContextMixin
from django.views.generic.edit import FormView
from mailing.mail_service import EmailSender
from tasks.models import MentorTaskMarkCriteriaApprenticeVideoValue
from users.decorators import apprentice_login_required, anonymous_required
from users.forms import ApprenticeAuthenticationForm, ApprenticeCreateForm, ApprenticeUpdateForm, \
    ApprenticePasswordResetForm, ApprenticePasswordChangeForm
from users.models import Apprentice
from utils.general import get_base_url_from_request


class TitleSubtitleContextMixin(ContextMixin):
    """Mixin uzupełniający context o tytuł i podtytuł widoczny z lewej strony"""
    title = ''
    subtitle = ''
    login_button = False

    def get_context_data(self, **kwargs):
        context = super(TitleSubtitleContextMixin, self).get_context_data(**kwargs)
        context['title'] = self.title
        context['subtitle'] = self.subtitle
        context['login_button'] = self.login_button
        return context


@anonymous_required
class LoginView(BaseLoginView, TitleSubtitleContextMixin):
    """Widok logowania użytkownika."""
    form_class = ApprenticeAuthenticationForm
    template_name = 'users/login.html'
    title = _('Twoje miejsce gdzie możesz prezentować siebie')
    subtitle = _('Doskonal sztukę prezentacji pod okiem mentorów, otrzymuj cenne uwagi i opinie od społeczności.')

    def get_context_data(self, **kwargs):
        context = super(LoginView, self).get_context_data(**kwargs)
        context['activation_info'] = self.request.session.pop('activation_info', None)
        return context


@anonymous_required
class RegisterView(FormView, TitleSubtitleContextMixin):
    template_name = 'users/register.html'
    form_class = ApprenticeCreateForm
    success_url = reverse_lazy('users:login')
    title = _('Twoje miejsce gdzie możesz prezentować siebie')
    subtitle = _('Doskonal sztukę prezentacji pod okiem mentorów, otrzymuj cenne uwagi i opinie od społeczności.')

    def form_valid(self, form):
        user = form.save()
        BASE_SITE_URL = get_base_url_from_request(self.request)
        EmailSender.send_registration_mail(user.email,
                                           {'BASE_SITE_URL': BASE_SITE_URL, 'activation_key': user.activation_key})
        self.request.session['activation_info'] = True
        return super(RegisterView, self).form_valid(form)


@anonymous_required
class ActivationView(TemplateView, TitleSubtitleContextMixin):
    """Widok aktywacji po rejestracji użytkownika."""
    template_name = 'users/generic.html'
    success_url = reverse_lazy('users:login')
    title_success = _('Świetnie!')
    subtitle_success = _('Twoje konto zostalo aktywowane, możesz teraz zalogować się do portalu.')
    title_error = _('Wystąpił problem')
    subtitle_error = _('Twoje konto było już wcześniej aktywowane, lub link jest nieprawidłowy.')
    login_button = True

    def get(self, request, *args, **kwargs):
        activation_key = kwargs.get('activation_key')
        try:
            apprentice = Apprentice.objects.get(activation_key=activation_key, is_active=False)
            apprentice.is_active = True
            apprentice.save()
            self.title = self.title_success
            self.subtitle = self.subtitle_success
        except (Apprentice.DoesNotExist, Apprentice.MultipleObjectsReturned):
            self.title = self.title_error
            self.subtitle = self.subtitle_error
        return super(ActivationView, self).get(request, *args, **kwargs)


@apprentice_login_required
class LogoutView(BaseLogoutView):
    """Widok wylogowania użytkownika."""
    next_page = 'users:login'


@apprentice_login_required
class ProfileView(FormView):
    """Widok profilu użytkownika."""
    template_name = 'users/profile.html'
    form_class = ApprenticeUpdateForm
    success_url = reverse_lazy('users:profile')

    def get_form(self, form_class=None):
        instance = self.request.user
        return ApprenticeUpdateForm(instance=instance, **self.get_form_kwargs())

    def form_valid(self, form):
        form.save(request=self.request)
        return super(ProfileView, self).form_valid(form)

    def get_context_data(self, **kwargs):
        context = super(ProfileView, self).get_context_data(**kwargs)

        mtmcavv = MentorTaskMarkCriteriaApprenticeVideoValue.objects.filter(Q(
            apprentice_video__task_answer_as_1__apprentice=self.request.user) | Q(
            apprentice_video__task_answer_as_2__apprentice=self.request.user))

        context['scores'] = mtmcavv.group_averages()
        context['average'] = mtmcavv.average()
        return context


@anonymous_required
class PasswordResetView(BasePasswordResetView, TitleSubtitleContextMixin):
    """Widok resetowania hasła użytkownika."""
    form_class = ApprenticePasswordResetForm
    success_url = reverse_lazy('users:password-reset-done')
    template_name = 'users/password_reset.html'
    title = _('Ustaw nowe hasło')
    subtitle = _('Podaj adres email który jest przypisany do Twojego konta')


@anonymous_required
class PasswordResetDoneView(TemplateView, TitleSubtitleContextMixin):
    """Widok resetowania hasła użytkownika - podsumowanie."""
    template_name = 'users/generic.html'
    title = _('Email wysłany')
    subtitle = _('Na podany adres email został wysłany link umożliwiający zmianę hasła')


@anonymous_required
class PasswordChangeView(BasePasswordResetConfirmView, TitleSubtitleContextMixin):
    """Widok zmiany hasła użytkownika."""
    form_class = ApprenticePasswordChangeForm
    title = _('Podaj hasło')
    subtitle = _('Możesz teraz ustawić nowe hasło do portalu')
    success_url = reverse_lazy('users:password-change-done')
    template_name = 'users/password_change.html'


@anonymous_required
class PasswordChangeDoneView(TemplateView, TitleSubtitleContextMixin):
    """Widok zmiany hasła użytkownika - podsumowanie."""
    template_name = 'users/generic.html'
    title = _('Hasło zostało ponownie ustawione')
    subtitle = _('Możesz teraz zalogować się do portalu')
    login_button = True
