from django.shortcuts import redirect, get_object_or_404 from django.urls import reverse_lazy from django.contrib.auth.decorators import login_required from django.contrib.auth.mixins import LoginRequiredMixin, UserPassesTestMixin from django.db.models import Count, OuterRef, Q, Subquery from django.views.generic import CreateView, DeleteView, ListView from django.http import HttpResponseRedirect from propositions.models import Answer, Proposition class PropositionCreate(LoginRequiredMixin, CreateView): template_name = "propositions/create.html" success_url = reverse_lazy("propositions:list") model = Proposition fields = ["name", "artist", "link"] def form_valid(self, form): proposition = form.save(commit=False) proposition.user = self.request.user proposition.save() return HttpResponseRedirect(self.success_url) class PropositionList(LoginRequiredMixin, ListView): template_name = "propositions/liste.html" context_object_name = "propositions" model = Proposition def get_queryset(self): user = self.request.user user_answers = ( Answer.objects .filter(proposition=OuterRef("id"), user=user) .values_list("answer", flat=True) ) return ( Proposition.objects .annotate(nb_yes=Count("answer", filter=Q(answer__answer=Answer.YES))) .annotate(nb_no=Count("answer", filter=Q(answer__answer=Answer.NO))) .annotate(user_answer=Subquery(user_answers[:1])) .order_by("-nb_yes", "nb_no", "name") ) class PropositionDelete(LoginRequiredMixin, UserPassesTestMixin, DeleteView): model = Proposition template_name = "propositions/delete.html" success_url = reverse_lazy("propositions:list") def test_func(self): proposition = self.get_object() user = self.request.user return (proposition.user == user or user.profile.is_chef) @login_required def answer(request, id, ans): proposition = get_object_or_404(Proposition, id=id) user = request.user Answer.objects.filter(proposition=proposition, user=user).delete() Answer.objects.create(proposition=proposition, user=user, answer=ans) return redirect("propositions:list")