This commit is contained in:
Ross
2022-05-21 22:13:11 +01:00
parent e61d00caa6
commit a5b7d2a680
2 changed files with 39 additions and 22 deletions
+12 -6
View File
@@ -42,7 +42,12 @@ import json
import statistics import statistics
import plotly.express as px import plotly.express as px
from generic.views import AuthorRequiredMixin, ExamCloneMixin, ExamViews, GenericViewBase from generic.views import (
AuthorRequiredMixin,
ExamCloneMixin,
ExamViews,
GenericViewBase,
)
from rest_framework import viewsets, permissions from rest_framework import viewsets, permissions
from rest_framework.pagination import PageNumberPagination from rest_framework.pagination import PageNumberPagination
@@ -311,7 +316,7 @@ def exam_take(request, pk, sk, cid, passcode):
) )
#def loadJsonAnswer(answer): # def loadJsonAnswer(answer):
# # As access is not restricted make sure the data appears valid # # As access is not restricted make sure the data appears valid
# if (not isinstance(answer["cid"], int)) or (not isinstance(answer["eid"], int)): # if (not isinstance(answer["cid"], int)) or (not isinstance(answer["eid"], int)):
# return False, JsonResponse({"success": False, "error": "invalid"}) # return False, JsonResponse({"success": False, "error": "invalid"})
@@ -368,9 +373,7 @@ def exam_take(request, pk, sk, cid, passcode):
# return True, None # return True, None
GenericExamViews = ExamViews( GenericExamViews = ExamViews(Exam, Question, None, CidUserAnswer, "physics", "physics")
Exam, Question, None, CidUserAnswer, "physics", "physics"
)
GenericViews = GenericViewBase("physics", Question, CidUserAnswer, Exam) GenericViews = GenericViewBase("physics", Question, CidUserAnswer, Exam)
@@ -391,10 +394,13 @@ class ExamClone(AuthorOrCheckerRequiredMixin, ExamCloneMixin, ExamCreate):
"""Clone exam view""" """Clone exam view"""
class ExamAuthorUpdate(RevisionMixin, LoginRequiredMixin, AuthorRequiredMixin, UpdateView): class ExamAuthorUpdate(
RevisionMixin, LoginRequiredMixin, AuthorRequiredMixin, UpdateView
):
model = Exam model = Exam
form_class = ExamAuthorForm form_class = ExamAuthorForm
class ExamDelete(RevisionMixin, AuthorOrCheckerRequiredMixin, DeleteView): class ExamDelete(RevisionMixin, AuthorOrCheckerRequiredMixin, DeleteView):
model = Exam model = Exam
template_name = "exam_confirm_delete.html" template_name = "exam_confirm_delete.html"
+27 -16
View File
@@ -42,7 +42,12 @@ from .models import (
CidUserAnswer, CidUserAnswer,
) )
from generic.views import AuthorRequiredMixin, ExamCloneMixin, ExamViews, GenericViewBase from generic.views import (
AuthorRequiredMixin,
ExamCloneMixin,
ExamViews,
GenericViewBase,
)
from reversion.views import RevisionMixin from reversion.views import RevisionMixin
@@ -350,8 +355,8 @@ class RapidUpdate(
def form_valid(self, form): def form_valid(self, form):
# save exam orders (there must be a better way to do this) # save exam orders (there must be a better way to do this)
#exam_orders = {} # exam_orders = {}
#for exam in self.object.exams.all(): # for exam in self.object.exams.all():
# exam_orders[exam] = list(exam.exam_questions.all()) # exam_orders[exam] = list(exam.exam_questions.all())
self.object = form.save(commit=False) self.object = form.save(commit=False)
@@ -371,8 +376,8 @@ class RapidUpdate(
answer_formset.save() answer_formset.save()
# restore exam orders # restore exam orders
#wanted_exams = form["exams"].data # wanted_exams = form["exams"].data
#for exam in self.object.exams.all(): # for exam in self.object.exams.all():
# if exam in exam_orders and self.object in exam_orders[exam]: # if exam in exam_orders and self.object in exam_orders[exam]:
# print(exam_orders[exam]) # print(exam_orders[exam])
# exam.exam_questions.set(exam_orders[exam]) # exam.exam_questions.set(exam_orders[exam])
@@ -509,7 +514,6 @@ class RapidView(LoginRequiredMixin, SingleTableMixin, FilterView):
filterset_class = RapidFilter filterset_class = RapidFilter
@login_required @login_required
def mark_all(request, exam_pk, sk): def mark_all(request, exam_pk, sk):
return mark(request, exam_pk, sk, unmarked_exam_answers_only=False) return mark(request, exam_pk, sk, unmarked_exam_answers_only=False)
@@ -673,7 +677,6 @@ def mark(request, exam_pk, sk, unmarked_exam_answers_only=True, review=False):
) )
def exam_scores_cid_user(request, pk, cid, passcode): def exam_scores_cid_user(request, pk, cid, passcode):
exam = get_object_or_404(Exam, pk=pk) exam = get_object_or_404(Exam, pk=pk)
@@ -682,13 +685,15 @@ def exam_scores_cid_user(request, pk, cid, passcode):
# TODO:Need some kind of test for cid # TODO:Need some kind of test for cid
questions = exam.exam_questions.all()#.prefetch_related("cid_user_answers", "answers") questions = (
exam.exam_questions.all()
) # .prefetch_related("cid_user_answers", "answers")
#cid_user_answers = list(CidUserAnswer.objects.filter(cid=cid, exam__id=pk).prefetch_related("question")) # cid_user_answers = list(CidUserAnswer.objects.filter(cid=cid, exam__id=pk).prefetch_related("question"))
#cid_user_answers_q_map = {} # cid_user_answers_q_map = {}
#for ans in cid_user_answers: # for ans in cid_user_answers:
# cid_user_answers_q_map[ans.question] = ans # cid_user_answers_q_map[ans.question] = ans
answers_and_marks = [] answers_and_marks = []
@@ -702,7 +707,7 @@ def exam_scores_cid_user(request, pk, cid, passcode):
for q in questions: for q in questions:
# Get user answer # Get user answer
user_answer = q.cid_user_answers.filter(cid=cid, exam__id=pk).first() user_answer = q.cid_user_answers.filter(cid=cid, exam__id=pk).first()
#user_answer = cid_user_answers_q_map[q] # user_answer = cid_user_answers_q_map[q]
if not user_answer or user_answer is None: if not user_answer or user_answer is None:
# skip if no answer # skip if no answer
@@ -762,9 +767,7 @@ class QuestionDelete(AuthorOrCheckerRequiredMixin, DeleteView):
success_url = reverse_lazy("rapids:rapid_view") success_url = reverse_lazy("rapids:rapid_view")
GenericExamViews = ExamViews( GenericExamViews = ExamViews(Exam, Rapid, Answer, CidUserAnswer, "rapids", "rapid")
Exam, Rapid, Answer, CidUserAnswer, "rapids", "rapid"
)
class ExamCreate(RevisionMixin, LoginRequiredMixin, CreateView): class ExamCreate(RevisionMixin, LoginRequiredMixin, CreateView):
@@ -793,18 +796,24 @@ class ExamUpdate(
return super().form_valid(form) return super().form_valid(form)
class ExamAuthorUpdate(RevisionMixin, LoginRequiredMixin, AuthorRequiredMixin, UpdateView):
class ExamAuthorUpdate(
RevisionMixin, LoginRequiredMixin, AuthorRequiredMixin, UpdateView
):
model = Exam model = Exam
form_class = ExamAuthorForm form_class = ExamAuthorForm
class ExamDelete(RevisionMixin, AuthorOrCheckerRequiredMixin, DeleteView): class ExamDelete(RevisionMixin, AuthorOrCheckerRequiredMixin, DeleteView):
model = Exam model = Exam
template_name = "exam_confirm_delete.html" template_name = "exam_confirm_delete.html"
success_url = reverse_lazy("rapids:index") success_url = reverse_lazy("rapids:index")
class UserAnswerView(LoginRequiredMixin, DetailView): class UserAnswerView(LoginRequiredMixin, DetailView):
model = CidUserAnswer model = CidUserAnswer
class UserAnswerTableView(LoginRequiredMixin, SingleTableMixin, FilterView): class UserAnswerTableView(LoginRequiredMixin, SingleTableMixin, FilterView):
model = CidUserAnswer model = CidUserAnswer
table_class = RapidUserAnswerTable table_class = RapidUserAnswerTable
@@ -921,6 +930,7 @@ class RapidLateralityViewSet(
GenericViews = GenericViewBase("rapids", Rapid, CidUserAnswer, Exam) GenericViews = GenericViewBase("rapids", Rapid, CidUserAnswer, Exam)
@user_is_author_or_rapid_checker @user_is_author_or_rapid_checker
def question_anonymise_dicom(request, pk): def question_anonymise_dicom(request, pk):
question = get_object_or_404(Rapid, pk=pk) question = get_object_or_404(Rapid, pk=pk)
@@ -929,6 +939,7 @@ def question_anonymise_dicom(request, pk):
return redirect("rapids:question_detail", pk=pk) return redirect("rapids:question_detail", pk=pk)
@user_is_author_or_rapid_checker @user_is_author_or_rapid_checker
def question_save_annotation(request, pk): def question_save_annotation(request, pk):
if request.is_ajax() and request.method == "POST": if request.is_ajax() and request.method == "POST":