Пример #1
0
class CatalogsPerSubjectRemarks(generics.RetrieveUpdateAPIView):
    permission_classes = (IsTeacher, )
    serializer_class = CatalogsPerSubjectRemarksSerializer
    lookup_field = 'id'
    http_method_names = [
        GET.lower(), PUT.lower(),
        OPTIONS.lower(),
        HEAD.lower()
    ]

    def get_queryset(self):
        profile = self.request.user.user_profile
        return StudentCatalogPerSubject.objects.filter(teacher_id=profile.id, )
Пример #2
0
class GradeDetail(UpdateAPIView, DestroyAPIView):
    permission_classes = (IsTeacher, )
    serializer_class = SubjectGradeUpdateSerializer
    http_method_names = [
        DELETE.lower(),
        PUT.lower(),
        OPTIONS.lower(),
        HEAD.lower()
    ]

    @lru_cache(maxsize=None)
    def get_object(self):
        return get_object_or_404(
            SubjectGrade.objects.select_related(
                'catalog_per_subject__study_class').prefetch_related(
                    'catalog_per_subject__absences',
                    'catalog_per_subject__examination_grades'),
            id=self.kwargs['id'],
            catalog_per_subject__teacher_id=self.request.user.user_profile)

    def check_grade_can_be_edited(self):
        grade = self.get_object()

        # TODO uncomment after it's tested
        # if not can_update_grades_or_absences(grade.catalog_per_subject.study_class):
        #     return Response({'message': _(f'Cannot {action} grades at this time.')},
        #                     status=status.HTTP_400_BAD_REQUEST)

    def update(self, request, *args, **kwargs):
        return self.check_grade_can_be_edited() or super().update(
            request, *args, **kwargs)

    def delete(self, request, *args, **kwargs):
        instance = self.get_object()
        catalog = instance.catalog_per_subject

        if catalog.is_coordination_subject:
            return Response(
                {'message': _("Can't delete coordination subject grade.")},
                status=status.HTTP_400_BAD_REQUEST)

        error = self.check_grade_can_be_edited()
        if error:
            return error

        instance.delete()

        compute_averages([catalog], instance.semester)
        update_last_change_in_catalog(request.user.user_profile)
        return Response(StudentCatalogPerSubjectSerializer(catalog).data)
Пример #3
0
class SchoolUnitDetail(generics.RetrieveUpdateAPIView):
    permission_classes = (IsAdministrator, )
    queryset = RegisteredSchoolUnit.objects.all()
    lookup_field = 'id'
    http_method_names = [
        GET.lower(), PUT.lower(),
        OPTIONS.lower(),
        HEAD.lower()
    ]

    def get_serializer_class(self):
        if self.request.method == PUT:
            return RegisteredSchoolUnitUpdateSerializer
        return RegisteredSchoolUnitDetailSerializer
Пример #4
0
class CurrentAcademicYearCalendar(RetrieveUpdateAPIView):
    permission_classes = (AcademicCalendarPermissionClass, )
    serializer_class = CurrentAcademicYearCalendarSerializer
    http_method_names = [
        GET.lower(), PUT.lower(),
        OPTIONS.lower(),
        HEAD.lower()
    ]

    def get_object(self):
        calendar = get_current_academic_calendar()
        if not calendar:
            raise Http404()

        return calendar
Пример #5
0
class MyAccountDetail(generics.RetrieveUpdateAPIView):
    permission_classes = (IsAuthenticated, )
    http_method_names = [
        GET.lower(), PUT.lower(),
        HEAD.lower(), OPTIONS.lower()
    ]

    def get_serializer_class(self):
        user_role = self.request.user.user_profile.user_role

        if user_role == UserProfile.UserRoles.STUDENT:
            return MyAccountStudentSerializer
        if user_role == UserProfile.UserRoles.PARENT:
            return MyAccountParentSerializer
        return MyAccountSerializer

    def get_object(self):
        return self.request.user.user_profile
class AcademicProgramDetail(generics.RetrieveUpdateDestroyAPIView):
    permission_classes = (IsPrincipal, )
    lookup_field = 'id'
    http_method_names = [
        GET.lower(),
        PATCH.lower(),
        DELETE.lower(),
        OPTIONS.lower(),
        HEAD.lower()
    ]

    def get_serializer_class(self):
        if self.request.method == PATCH:
            return AcademicProgramUpdateSerializer
        return AcademicProgramDetailSerializer

    def get_serializer_context(self):
        context = super().get_serializer_context()
        context.update({
            'generic_academic_program_id':
            self.get_object().generic_academic_program_id,
            'academic_year':
            self.get_object().academic_year,
            'school_unit':
            self.request.user.user_profile.school_unit
        })
        return context

    def get_queryset(self):
        return AcademicProgram.objects.filter(
            school_unit=self.request.user.user_profile.school_unit)

    @lru_cache(maxsize=None)
    def get_object(self):
        return super().get_object()

    def delete(self, request, *args, **kwargs):
        program = self.get_object()
        if program.classes_count > 0:
            return Response(
                {
                    'message':
                    _("Cannot delete an academic program that still has study classes assigned."
                      )
                },
                status=status.HTTP_400_BAD_REQUEST)

        return self.destroy(request, *args, **kwargs)

    def partial_update(self, request, *args, **kwargs):
        current_academic_year_calendar = get_current_academic_calendar()

        if not current_academic_year_calendar:
            raise Http404()

        if current_academic_year_calendar.academic_year != self.get_object(
        ).academic_year:
            return Response(
                {
                    'message':
                    _('Invalid year, must be the current academic year.')
                },
                status=status.HTTP_400_BAD_REQUEST)

        # TODO uncomment after it's tested
        # if timezone.now().date() > datetime.date(current_academic_year_calendar.created.year, 9, 15):
        #     return Response(
        #         {'message': _('Academic programs must be updated before 15th of September of the current year.')},
        #         status=status.HTTP_400_BAD_REQUEST
        #     )

        return super().partial_update(request, *args, **kwargs)
Пример #7
0
class ExaminationGradeDetail(generics.UpdateAPIView, generics.DestroyAPIView):
    permission_classes = (IsTeacher, )
    serializer_class = ExaminationGradeUpdateSerializer
    http_method_names = [
        DELETE.lower(),
        PUT.lower(),
        OPTIONS.lower(),
        HEAD.lower()
    ]

    @lru_cache(maxsize=None)
    def get_object(self):
        return get_object_or_404(
            ExaminationGrade.objects.select_related(
                'catalog_per_subject__study_class').prefetch_related(
                    'catalog_per_subject__grades',
                    'catalog_per_subject__absences'),
            id=self.kwargs['id'],
            catalog_per_subject__teacher_id=self.request.user.user_profile)

    def check_grade_can_be_edited(self):
        examination_grade = self.get_object()

        action = _('delete') if self.request.method == DELETE else _('update')
        if examination_grade.created < timezone.now() - timezone.timedelta(
                hours=2):
            return Response(
                {
                    'message':
                    _('Cannot {} a grade that was created more than 2 hours ago.'
                      ).format(action)
                },
                status=status.HTTP_400_BAD_REQUEST)

        if not can_update_examination_grades(
                examination_grade.catalog_per_subject.study_class,
                examination_grade.grade_type):
            return Response(
                {
                    'message':
                    _('Cannot {} grades at this time.').format(action)
                },
                status=status.HTTP_400_BAD_REQUEST)

    def update(self, request, *args, **kwargs):
        return self.check_grade_can_be_edited() or super().update(
            request, *args, **kwargs)

    def delete(self, request, *args, **kwargs):
        error = self.check_grade_can_be_edited()
        if error:
            return error

        instance = self.get_object()
        instance.delete()

        change_averages_after_examination_grade_operation(
            [instance.catalog_per_subject], instance.grade_type,
            instance.semester)
        update_last_change_in_catalog(request.user.user_profile)

        return Response(
            StudentCatalogPerSubjectSerializer(
                instance.catalog_per_subject).data)
Пример #8
0
class UserProfileDetail(UserProfileDetailBase,
                        generics.RetrieveUpdateDestroyAPIView):
    http_method_names = [
        GET.lower(),
        PUT.lower(),
        DELETE.lower(),
        HEAD.lower(),
        OPTIONS.lower()
    ]

    def get_queryset(self):
        if self.request.method in [PUT, DELETE]:
            return super().get_queryset()

        profile = self.request.user.user_profile

        school_filter = {}
        if profile.user_role == UserProfile.UserRoles.ADMINISTRATOR:
            user_roles = [
                UserProfile.UserRoles.ADMINISTRATOR,
                UserProfile.UserRoles.PRINCIPAL
            ]
        else:
            school_filter['school_unit'] = profile.school_unit_id
            if profile.user_role == UserProfile.UserRoles.PRINCIPAL:
                user_roles = [
                    UserProfile.UserRoles.TEACHER,
                    UserProfile.UserRoles.PARENT, UserProfile.UserRoles.STUDENT
                ]
            elif profile.user_role == UserProfile.UserRoles.TEACHER:
                user_roles = [
                    UserProfile.UserRoles.TEACHER,
                    UserProfile.UserRoles.PARENT, UserProfile.UserRoles.STUDENT
                ]
            else:
                user_roles = [
                    UserProfile.UserRoles.PRINCIPAL,
                    UserProfile.UserRoles.TEACHER
                ]

        return UserProfile.objects.select_related('user', 'student_in_class') \
            .filter(user_role__in=user_roles, user__is_staff=False, **school_filter)

    @staticmethod
    def has_assigned_study_classes(teacher):
        current_academic_calendar = get_current_academic_calendar()
        if current_academic_calendar is None:
            return False

        return teacher.teacher_class_through.filter(
            academic_year=current_academic_calendar.academic_year).exists()

    def delete(self, request, *args, **kwargs):
        requested_profile = self.get_object()
        if requested_profile.last_online or \
                (requested_profile.user_role == UserProfile.UserRoles.PRINCIPAL and
                 getattr(requested_profile, 'registered_school_unit', None)) or \
                (requested_profile.user_role == UserProfile.UserRoles.TEACHER and
                 self.has_assigned_study_classes(requested_profile)) or \
                (requested_profile.user_role == UserProfile.UserRoles.STUDENT and
                 (SubjectGrade.objects.filter(student=requested_profile).exists() or
                  SubjectAbsence.objects.filter(student=requested_profile).exists() or
                  ExaminationGrade.objects.filter(student=requested_profile).exists())):
            return Response(
                {
                    'message':
                    _("This user cannot be deleted because it's either active or has data."
                      )
                },
                status=status.HTTP_400_BAD_REQUEST)

        user = requested_profile.user
        requested_profile.delete()
        user.delete()

        return Response(status=status.HTTP_204_NO_CONTENT)