def validate(self, data: dict) -> dict: """ Zvaliduje účast. """ # u predplacene lekce nelze menit parametry platby if self.instance and self.instance.lecture.start is None: LectureHelpers.validate_prepaid_non_changable_paid_state(data) return data
def update(self, instance: Attendance, validated_data: dict) -> Attendance: """ Upraví účast a provede další nutné transformace dat. """ attendancestate_old = instance.attendancestate canceled_old = instance.lecture.canceled # uprava instance ucasti instance = super().update(instance, validated_data) # proved korekce poctu predplacenych lekci LectureHelpers.lecture_corrections(instance.lecture, instance, canceled_old, attendancestate_old) # nastav lekci jako zrusenou pokud nikdo nema prijit LectureHelpers.cancel_lecture_if_nobody_arrives(instance.lecture) return instance
def get_number(obj: Lecture) -> Union[int, str, None]: """ Vypočítá pořadové číslo lekce. Pokud se jedná o předplacenou lekci, vrátí None. Pokud se nedá číslo dopočítat kvůli chybějícímu výchozímu stavu účasti, vrátí upozornění. """ # vrat null pokud se jedna o predplacenou lekci if obj.start is None: return None # proved jednoduchy vypocet poradoveho cisla pro skupinu if obj.group is not None: prev_lectures_cnt = Lecture.objects.filter( group=obj.group, start__isnull=False, start__lt=obj.start, canceled=False ).count() else: # proved vypocet poradoveho cisla pro jednotlivce try: # je potreba najit vychozi stav attendancestate_default_pk = LectureHelpers.find_default_state() except ObjectDoesNotExist: # pokud neni vychozi stav zvoleny, vrat misto toho upozorneni return LectureHelpers.DEFAULT_STATE_MISSING prev_lectures_cnt = Attendance.objects.filter( client=obj.attendances.get().client_id, lecture__course=obj.course, lecture__start__isnull=False, lecture__group__isnull=True, lecture__start__lt=obj.start, lecture__canceled=False, attendancestate=attendancestate_default_pk, ).count() # vrat poradove cislo aktualni lekce (tedy +1 k poctu minulych lekci) return prev_lectures_cnt + 1
def get_number(obj: Attendance) -> Union[int, str, None]: """ Vypočítá pořadové číslo lekce pro daného klienta skupiny. Pro jednotlivce se pole nezobrazuje, tedy neni treba nic pocitat. Pokud se nedá číslo dopočítat kvůli chybějícímu výchozímu stavu účasti, vrátí upozornění. """ # pro lekce jednotlivcu pole neukazujeme, tedy nic neni treba pocitat if not obj.lecture.group: return None # proved vypocet poradoveho cisla pro ucastnika skupinove lekce try: # je potreba najit vychozi stav attendancestate_default_pk = LectureHelpers.find_default_state() except ObjectDoesNotExist: # pokud neni vychozi stav zvoleny, vrat misto toho upozorneni return LectureHelpers.DEFAULT_STATE_MISSING prev_lectures_cnt = Attendance.objects.filter( client=obj.client, lecture__course=obj.lecture.course, lecture__group=obj.lecture.group, lecture__start__lt=obj.lecture.start, lecture__canceled=False, attendancestate=attendancestate_default_pk, ).count() # vrat poradove cislo aktualni lekce (tedy +1 k poctu minulych lekci) return prev_lectures_cnt + 1
def create(self, validated_data: dict) -> Lecture: """ Vytvoří lekci a k ní příslušející účasti klientů, provede další nutné transformace. """ # pro create se refresh_clients nepouziva, muzeme smazat validated_data.pop("refresh_clients") # vytvoreni instance lekce attendances_data = validated_data.pop("attendances") group = validated_data.pop("group", None) # kurz vezmi z dat, v pripade skupiny primo z ni course = validated_data.pop( "course") if "course" in validated_data else group.course # nastav lekci jako zrusenou pokud nikdo nema prijit if not validated_data["canceled"]: validated_data[ "canceled"] = LectureHelpers.find_if_lecture_should_be_canceled( attendances_data) instance = Lecture.objects.create(course=course, group=group, **validated_data) # vytvoreni jednotlivych ucasti for attendance_data in attendances_data: client = attendance_data.pop("client") # OMEZENÍ O8: pokud klient neni aktivni, nastav ho jako aktivniho if not client.active: client.active = True client.save() # OMEZENÍ O7: pokud se jedna o skupinu, proved korekce poctu predplacenych lekci if group is not None: # najdi clenstvi nalezici klientovi v teto skupine try: membership = group.memberships.get(client=client) except ObjectDoesNotExist: # pokud uz klient neni clenem skupiny, nic nedelej pass else: # pokud ma dorazit, lekce neni zrusena a ma nejake predplacene lekce, odecti jednu if (not instance.canceled and attendance_data["attendancestate"].default and membership.prepaid_cnt > 0): attendance_data.paid = True membership.prepaid_cnt = membership.prepaid_cnt - 1 membership.save() Attendance.objects.create(client=client, lecture=instance, **attendance_data) return instance
def update(self, instance: Lecture, validated_data: dict) -> Lecture: # type: ignore """ Upraví lekci a k ní příslušející účasti klientů, provede další nutné transformace. """ canceled_old = instance.canceled attendances_data = validated_data.pop("attendances", None) # uprava instance lekce instance = super().update(instance, validated_data) # pokud nejsou zaslany ucasti, update konci if not attendances_data: return instance # upravy jednotlivych ucasti attendances = instance.attendances.all() refresh_clients = validated_data["refresh_clients"] for attendance_data in attendances_data: # najdi prislusnou ucast attendance = attendances.get(pk=attendance_data["id"]) # projeveni zmen klientu skupiny (smazani ucasti) if instance.group and refresh_clients: # pokud ucastnik uz neni clenem skupiny, smaz jeho ucast a prejdi na dalsiho ucastnika try: instance.group.memberships.get(client=attendance.client) except ObjectDoesNotExist: attendance.delete() continue # jedna se stale o clena skupiny (nebo neni pozadovano projeveni zmen klientu), proved prislusne upravy attendancestate_old = attendance.attendancestate # uprava ucasti attendance = super().update(attendance, attendance_data) # proved korekce poctu predplacenych lekci LectureHelpers.lecture_corrections(instance, attendance, canceled_old, attendancestate_old) # projeveni zmen klientu skupiny (pridani ucasti) if instance.group and refresh_clients: LectureHelpers.refresh_clients_add(instance, attendances_data) # nastav lekci jako zrusenou pokud nikdo nema prijit LectureHelpers.cancel_lecture_if_nobody_arrives(instance) return instance
def validate(self, data: dict) -> dict: """ Zvaliduje lekci. """ # skupina, ktere patri tato lekce is_group = LectureHelpers.is_group(data, self.instance) # validace kurzu LectureHelpers.validate_course_presence(data, self.instance, is_group) # validace poctu ucastniku lekce LectureHelpers.validate_attendants_count(data, is_group) # validace start & duration LectureHelpers.validate_start_duration(data, is_group) # pro nove predplacene lekce proved jen jednoduchou kontrolu (nelze menit parametry platby) if "start" in data and data["start"] is None: attendances = [] if "attendances" in data: attendances = data["attendances"] elif self.instance: attendances = self.instance.attendances for attendance in attendances: LectureHelpers.validate_prepaid_non_changable_paid_state(attendance) return data # kontrola casoveho konfliktu LectureHelpers.validate_lecture_collision(data, self.instance) return data