diff --git a/CHANGELOG.rst b/CHANGELOG.rst index 4222609531b74ee07ca97ff4f53cc1711c95839c..e88765a522ee299d86ed6d2965ead5ef22035c74 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -9,7 +9,8 @@ New features * Two-factor authentication with TOTP (Google Authenticator), Yubikey, SMS and phone call. - +* Devs: CRUDMixin provides a crud_event relation that returns all CRUD + events for an object `1.0a2`_ -------- diff --git a/biscuit/core/migrations/0001_initial.py b/biscuit/core/migrations/0001_initial.py index d0c78a5ae09b6a42c6721bc7d64b741e94ad6877..7c102208e5948130d1beef10bb38f99a76d70651 100644 --- a/biscuit/core/migrations/0001_initial.py +++ b/biscuit/core/migrations/0001_initial.py @@ -70,7 +70,7 @@ class Migration(migrations.Migration): ('import_ref', models.CharField(blank=True, editable=False, max_length=64, null=True, verbose_name='Reference ID of import source')), ('guardians', models.ManyToManyField(related_name='children', to='core.Person', verbose_name='Guardians / Parents')), ('primary_group', models.ForeignKey(null=True, on_delete=django.db.models.deletion.SET_NULL, to='core.Group')), - ('school', models.ForeignKey(default=biscuit.core.util.core_helpers.get_current_school, on_delete=django.db.models.deletion.CASCADE, to='core.School')), + ('school', models.ForeignKey(default=l, on_delete=django.db.models.deletion.CASCADE, to='core.School')), ('user', models.OneToOneField(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, related_name='person', to=settings.AUTH_USER_MODEL)), ], options={ @@ -96,7 +96,7 @@ class Migration(migrations.Migration): migrations.AddField( model_name='group', name='school', - field=models.ForeignKey(default=biscuit.core.util.core_helpers.get_current_school, on_delete=django.db.models.deletion.CASCADE, to='core.School'), + field=models.ForeignKey(default=1, on_delete=django.db.models.deletion.CASCADE, to='core.School'), ), migrations.AlterUniqueTogether( name='group', diff --git a/biscuit/core/migrations/0002_school_term.py b/biscuit/core/migrations/0002_school_term.py index e3d25010df8d9f81116e2c5d1ccb7b7516a3f9bd..9d905361b52140d6cbe844ccfe9f9acb4b7b6bce 100644 --- a/biscuit/core/migrations/0002_school_term.py +++ b/biscuit/core/migrations/0002_school_term.py @@ -32,7 +32,7 @@ class Migration(migrations.Migration): ('caption', models.CharField(max_length=30, verbose_name='Visible caption of the term')), ('date_start', models.DateField(null=True, verbose_name='Effective start date of term')), ('date_end', models.DateField(null=True, verbose_name='Effective end date of term')), - ('school', models.ForeignKey(default=biscuit.core.util.core_helpers.get_current_school, on_delete=django.db.models.deletion.CASCADE, to='core.School')), + ('school', models.ForeignKey(default=1, on_delete=django.db.models.deletion.CASCADE, to='core.School')), ], options={ 'abstract': False, diff --git a/biscuit/core/mixins.py b/biscuit/core/mixins.py index 024dd4870d076da301dd3c51be1a0e603e399144..bc482a343def9cf6034e7bb0cb7212623c07693e 100644 --- a/biscuit/core/mixins.py +++ b/biscuit/core/mixins.py @@ -69,16 +69,10 @@ class ExtensibleModel(object): cls._safe_add(func, func.__name__) - -class SchoolRelated(models.Model): +class CRUDMixin(models.Model): class Meta: abstract = True -# objects = SchoolRelatedManager() - - school = models.ForeignKey( - 'core.School', on_delete=models.CASCADE, default=get_current_school) - @property def crud_events(self) -> QuerySet: """Get all CRUD events connected to this object from easyaudit.""" diff --git a/biscuit/core/models.py b/biscuit/core/models.py index 9260fcbd3cd600240bb3967d2a6d4888a22928aa..d6e36c70bab00585aceb19d97318253287bd0731 100644 --- a/biscuit/core/models.py +++ b/biscuit/core/models.py @@ -7,7 +7,7 @@ from django.utils.translation import ugettext_lazy as _ from image_cropping import ImageCropField, ImageRatioField from phonenumber_field.modelfields import PhoneNumberField -from .mixins import ExtensibleModel, SchoolRelated +from .mixins import CRUDMixin, ExtensibleModel class School(models.Model): @@ -30,7 +30,7 @@ class School(models.Model): ordering = ['name', 'name_official'] -class SchoolTerm(SchoolRelated): +class SchoolTerm(models.Model): """ Information about a term (limited time frame) that data can be linked to. """ @@ -44,13 +44,12 @@ class SchoolTerm(SchoolRelated): 'Effective end date of term'), null=True) -class Person(SchoolRelated, ExtensibleModel): +class Person(ExtensibleModel): """ A model describing any person related to a school, including, but not limited to, students, teachers and guardians (parents). """ class Meta: - unique_together = [['school', 'short_name'], ['school', 'import_ref']] ordering = ['last_name', 'first_name'] SEX_CHOICES = [ @@ -70,7 +69,7 @@ class Person(SchoolRelated, ExtensibleModel): 'Additional name(s)'), max_length=30, blank=True) short_name = models.CharField(verbose_name=_( - 'Short name'), max_length=5, blank=True, null=True) + 'Short name'), max_length=5, blank=True, null=True, unique=True) street = models.CharField(verbose_name=_( 'Street'), max_length=30, blank=True) @@ -96,7 +95,8 @@ class Person(SchoolRelated, ExtensibleModel): photo_cropping = ImageRatioField('photo', '600x800', size_warning=True) import_ref = models.CharField(verbose_name=_( - 'Reference ID of import source'), max_length=64, blank=True, null=True, editable=False) + 'Reference ID of import source'), max_length=64, + blank=True, null=True, editable=False, unique=True) guardians = models.ManyToManyField('self', verbose_name=_('Guardians / Parents'), symmetrical=False, related_name='children') @@ -132,19 +132,18 @@ class Person(SchoolRelated, ExtensibleModel): return self.full_name -class Group(SchoolRelated, ExtensibleModel): +class Group(ExtensibleModel): """Any kind of group of persons in a school, including, but not limited classes, clubs, and the like. """ class Meta: - unique_together = [['school', 'name'], ['school', 'short_name']] ordering = ['short_name', 'name'] name = models.CharField(verbose_name=_( - 'Long name of group'), max_length=60) + 'Long name of group'), max_length=60, unique=True) short_name = models.CharField(verbose_name=_( - 'Short name of group'), max_length=16) + 'Short name of group'), max_length=16, unique=True) members = models.ManyToManyField('Person', related_name='member_of') owners = models.ManyToManyField('Person', related_name='owner_of') diff --git a/biscuit/core/util/core_helpers.py b/biscuit/core/util/core_helpers.py index bf19da058ae245bf4e9f47247c40786ab1d2d761..e8c0b1fe28c167b25f39eae946077c2d28832723 100644 --- a/biscuit/core/util/core_helpers.py +++ b/biscuit/core/util/core_helpers.py @@ -29,10 +29,6 @@ def get_app_packages() -> Sequence[str]: return pkgs -def get_current_school() -> int: - return 1 - - def is_impersonate(request: HttpRequest) -> bool: if hasattr(request, 'user'): return getattr(request.user, 'is_impersonate', False) diff --git a/biscuit/core/views.py b/biscuit/core/views.py index a32b9abe19b3131304c0a568d643a8336acd70d1..585d049ae72bd65c0a8ffd16bba88056850f2f04 100644 --- a/biscuit/core/views.py +++ b/biscuit/core/views.py @@ -10,7 +10,7 @@ from django_cron.models import CronJobLog from .decorators import admin_required from .forms import PersonsAccountsFormSet, EditPersonForm, EditGroupForm, EditSchoolForm, EditTermForm -from .models import Person, Group +from .models import Person, Group, School from .tables import PersonsTable, GroupsTable from .util import messages @@ -198,7 +198,7 @@ def school_management(request: HttpRequest) -> HttpResponse: def edit_school(request: HttpRequest) -> HttpResponse: context = {} - school = request.user.person.school + school = School.objects.first() edit_school_form = EditSchoolForm(request.POST or None, request.FILES or None, instance=school) context['school'] = school @@ -219,7 +219,7 @@ def edit_school(request: HttpRequest) -> HttpResponse: def edit_schoolterm(request: HttpRequest) -> HttpResponse: context = {} - term = request.user.person.school.current_term + term = School.objects.first().current_term edit_term_form = EditTermForm(request.POST or None, instance=term) if request.method == 'POST':