Skip to content
Snippets Groups Projects
Verified Commit bfed8756 authored by Jonathan Weth's avatar Jonathan Weth :keyboard:
Browse files

Fix type hints and add missing docstrings

parent d546eb54
No related branches found
No related tags found
1 merge request!120Resolve "Support events and extra lessons in class register"
Pipeline #5904 passed
......@@ -9,13 +9,22 @@ from django.utils.translation import gettext as _
from calendarweek import CalendarWeek
from aleksis.apps.alsijil.managers import PersonalNoteQuerySet
from aleksis.apps.chronos.models import Event, ExtraLesson, LessonPeriod
from aleksis.core.models import Group, Person
from .models import ExcuseType, ExtraMark, LessonDocumentation, PersonalNote
def alsijil_url(self, week: Optional[CalendarWeek] = None):
def alsijil_url(
self: Union[LessonPeriod, Event, ExtraLesson], week: Optional[CalendarWeek] = None
) -> str:
"""Build URL for the detail page of register objects.
Works with `LessonPeriod`, `Event` and `ExtraLesson`.
On `LessonPeriod` objects, it will work with annotated or passed weeks.
"""
if isinstance(self, LessonPeriod):
week = week or self.week
return reverse("lesson_period", args=[week.year, week.week, self.pk])
......@@ -45,8 +54,8 @@ def mark_absent(
):
"""Mark a person absent for all lessons in a day, optionally starting with a selected period number.
This function creates `PersonalNote` objects for every `LessonPeriod` the person
participates in on the selected day and marks them as absent/excused.
This function creates `PersonalNote` objects for every `LessonPeriod` and `ExtraLesson`
the person participates in on the selected day and marks them as absent/excused.
:param dry_run: With this activated, the function won't change any data
and just return the count of affected lessons
......@@ -115,10 +124,15 @@ def mark_absent(
return lesson_periods.count() + extra_lessons.count()
def get_personal_notes(self, persons: QuerySet, wanted_week: Optional[CalendarWeek] = None):
"""Get all personal notes for that lesson in a specified week.
def get_personal_notes(
self, persons: QuerySet, wanted_week: Optional[CalendarWeek] = None
) -> PersonalNoteQuerySet:
"""Get all personal notes for that register object in a specified week.
The week is optional for extra lessons and events as they have own date information.
Returns all linked `PersonalNote` objects, filtered by the given weeek,
Returns all linked `PersonalNote` objects,
filtered by the given week for `LessonPeriod` objects,
creating those objects that haven't been created yet.
..note:: Only available when AlekSIS-App-Alsijil is installed.
......@@ -253,7 +267,7 @@ def get_absences(self, week: Optional[CalendarWeek] = None) -> Iterator:
)
def get_absences_simple(self, week: Optional[CalendarWeek] = None) -> Iterator:
def get_absences_simple(self, week: Optional[CalendarWeek] = None) -> PersonalNoteQuerySet:
"""Get all personal notes of absent persons for this event/extra lesson."""
return self.personal_notes.all()
......
......@@ -88,8 +88,13 @@ lesson_related_constraint_q = (
class RegisterObjectRelatedMixin(WeekRelatedMixin):
"""Mixin with common API for lesson documentations and personal notes."""
@property
def register_object(self) -> Union[LessonPeriod, Event, ExtraLesson]:
def register_object(
self: Union["LessonDocumentation", "PersonalNote"]
) -> Union[LessonPeriod, Event, ExtraLesson]:
"""Get the object related to this lesson documentation or personal note."""
if self.lesson_period:
return self.lesson_period
elif self.event:
......@@ -98,23 +103,38 @@ class RegisterObjectRelatedMixin(WeekRelatedMixin):
return self.extra_lesson
@property
def calendar_week(self) -> CalendarWeek:
def calendar_week(self: Union["LessonDocumentation", "PersonalNote"]) -> CalendarWeek:
"""Get the calendar week of this lesson documentation or personal note.
.. note::
As events can be longer than one week,
this will return the week of the start date for events.
"""
if self.lesson_period:
return CalendarWeek(week=self.week, year=self.year,)
return CalendarWeek(week=self.week, year=self.year)
elif self.extra_lesson:
return self.extra_lesson.calendar_week
else:
return CalendarWeek.from_date(self.register_object.date_start)
@property
def school_term(self) -> SchoolTerm:
def school_term(self: Union["LessonDocumentation", "PersonalNote"]) -> SchoolTerm:
"""Get the school term of the related register object."""
if self.lesson_period:
return self.lesson_period.lesson.validity.school_term
else:
return self.register_object.school_term
@property
def date(self) -> Optional[date]:
def date(self: Union["LessonDocumentation", "PersonalNote"]) -> Optional[date]:
"""Get the date of this lesson documentation or personal note.
:: warning::
As events can be longer than one day,
this will return `None` for events.
"""
if self.lesson_period:
return super().date
elif self.extra_lesson:
......@@ -122,14 +142,20 @@ class RegisterObjectRelatedMixin(WeekRelatedMixin):
return None
@property
def date_formatted(self) -> str:
def date_formatted(self: Union["LessonDocumentation", "PersonalNote"]) -> str:
"""Get a formatted version of the date of this object.
Lesson periods, extra lessons: formatted date
Events: formatted date range
"""
return (
date_format(self.date)
if self.date
else f"{self.event.date_start}{self.event.date_end}"
else f"{date_format(self.event.date_start)}{date_format(self.event.date_end)}"
)
def get_absolute_url(self) -> str:
def get_absolute_url(self: Union["LessonDocumentation", "PersonalNote"]) -> str:
"""Get the absolute url of the detail view for the related register object."""
return self.register_object.get_alsijil_url(self.calendar_week)
......@@ -204,6 +230,7 @@ class PersonalNote(RegisterObjectRelatedMixin, ExtensibleModel):
return f"{self.date_formatted}, {self.lesson_period}, {self.person}"
def get_absolute_url(self) -> str:
"""Get the absolute url of the detail view for the related register object."""
return super().get_absolute_url() + "#personal-notes"
class Meta:
......@@ -283,7 +310,7 @@ class LessonDocumentation(RegisterObjectRelatedMixin, ExtensibleModel):
if changed:
lesson_documentation.save()
def __str__(self):
def __str__(self) -> str:
return f"{self.lesson_period}, {self.date_formatted}"
def save(self, *args, **kwargs):
......
......@@ -58,7 +58,7 @@ def get_timetable_instance_by_pk(
def annotate_documentations(
klass: Union[Event, LessonPeriod, ExtraLesson], wanted_week: CalendarWeek, pks: List[int]
) -> QuerySet:
"""Return a annotated queryset of all provided register objects."""
if isinstance(klass, LessonPeriod):
prefetch = Prefetch(
"documentations",
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment