Files
LMS/lmsege/lms/views.py
T
2026-09-19 15:38:50 +03:00

157 lines
6.7 KiB
Python

from django.shortcuts import render, get_object_or_404, redirect
from django.db.models import Q
from django.contrib.auth.decorators import login_required, user_passes_test
from django.utils.html import strip_tags
from .models import Assignment, Submission, Answer
import json
from .forms import AnswersForm, StudentRegistrationForm
from django.contrib.auth import login
def register(request):
if request.user.is_authenticated:
return redirect('lms:dashboard')
if request.method == 'POST':
form = StudentRegistrationForm(request.POST)
if form.is_valid():
user = form.save(commit=False)
user.role = 'STUDENT'
user.save()
login(request, user)
return redirect('lms:dashboard')
else:
form = StudentRegistrationForm()
return render(request, 'lms/register.html', {'form': form})
def is_student(user):
return user.is_authenticated and user.role == 'STUDENT'
def home(request):
if request.user.is_authenticated:
if getattr(request.user, 'role', None) == 'STUDENT':
return redirect('lms:dashboard')
else:
return redirect('/admin/')
return render(request, 'lms/home.html')
@login_required
@user_passes_test(is_student, login_url='/login/')
def dashboard(request):
assignments = Assignment.objects.filter(
Q(assign_to_all=True) | Q(assigned_students=request.user),
is_published=True
).distinct().order_by('-created_at')
# Check which ones the student has submitted
submissions = Submission.objects.filter(student=request.user)
submitted_assignment_ids = submissions.values_list('assignment_id', flat=True)
return render(request, 'lms/dashboard.html', {
'assignments': assignments,
'submitted_assignment_ids': submitted_assignment_ids,
'submissions': {sub.assignment_id: sub for sub in submissions}
})
@login_required
@user_passes_test(is_student, login_url='/login/')
def assignment_detail(request, pk):
assignment = get_object_or_404(Assignment, pk=pk, is_published=True)
questions = assignment.questions.all()
# Try to get existing submission
submission = Submission.objects.filter(assignment=assignment, student=request.user).first()
if submission:
if request.method == 'POST':
# Do not allow updating
return redirect('lms:dashboard')
form = None
else:
if request.method == 'POST':
form = AnswersForm(request.POST, request.FILES, questions=questions)
if form.is_valid():
submission = Submission.objects.create(assignment=assignment, student=request.user)
all_auto = True
total_points = 0
max_points = 0
for q in questions:
answer_obj = Answer(submission=submission, question=q)
if q.question_type == 'TEXT_AUTO':
val = form.cleaned_data.get(f'answer_{q.id}', '')
answer_obj.text_answer = val
if q.correct_answer:
correct = strip_tags(q.correct_answer).strip().lower()
answer_obj.is_correct = (val.strip().lower() == correct)
answer_obj.points = 1 if answer_obj.is_correct else 0
total_points += answer_obj.points
else:
all_auto = False
max_points += 1
elif q.question_type == 'TABLE_AUTO':
rows = getattr(q, 'table_rows', 2) or 2
table_data = []
for i in range(1, rows + 1):
val1 = form.cleaned_data.get(f'answer_{q.id}_r{i}_c1', '')
val2 = form.cleaned_data.get(f'answer_{q.id}_r{i}_c2', '')
table_data.append([val1, val2])
answer_obj.text_answer = json.dumps(table_data)
if q.correct_answer:
correct_rows = q.correct_answer.split(';')
is_correct = True
if len(correct_rows) != rows:
is_correct = False
else:
for i, row in enumerate(correct_rows):
cols = row.split('|')
if len(cols) == 2:
if cols[0].strip().lower() != table_data[i][0].strip().lower() or cols[1].strip().lower() != table_data[i][1].strip().lower():
is_correct = False
break
else:
is_correct = False
break
answer_obj.is_correct = is_correct
answer_obj.points = 1 if is_correct else 0
total_points += answer_obj.points
else:
all_auto = False
max_points += 1
else:
all_auto = False
val = form.cleaned_data.get(f'file_{q.id}')
if val:
answer_obj.file_answer = val
answer_obj.save()
if all_auto and max_points > 0:
submission.status = 'GRADED'
submission.grade = f"{total_points}/{max_points}"
else:
submission.status = 'PENDING'
submission.save()
return redirect('lms:dashboard')
else:
form = AnswersForm(questions=questions)
question_fields = []
if form:
for q in questions:
if q.question_type == 'TEXT_AUTO':
question_fields.append((q, 'text', form[f'answer_{q.id}']))
elif q.question_type == 'TABLE_AUTO':
rows = getattr(q, 'table_rows', 2) or 2
table_fields = []
for i in range(1, rows + 1):
table_fields.append([form[f'answer_{q.id}_r{i}_c1'], form[f'answer_{q.id}_r{i}_c2']])
question_fields.append((q, 'table', table_fields))
else:
question_fields.append((q, 'file', form[f'file_{q.id}']))
return render(request, 'lms/assignment_detail.html', {
'assignment': assignment,
'form': form,
'submission': submission,
'questions': questions,
'question_fields': question_fields,
})