diff --git a/src/lizaalert/courses/admin.py b/src/lizaalert/courses/admin.py index bd4fdf06..3d43665f 100644 --- a/src/lizaalert/courses/admin.py +++ b/src/lizaalert/courses/admin.py @@ -258,11 +258,7 @@ class KnowledgeAdmin(BaseAdmin): inlines = (CourseKnowledgeInline,) ordering = ("-updated_at",) - list_display = ( - "title", - "author", - "updated_at", - ) + list_display = ("title", "author", "created_at", "updated_at") @admin.register(Lesson) @@ -310,20 +306,22 @@ class SubscriptionAdmin(BaseAdmin): @admin.register(Division) -class DivisionAdmin(admin.ModelAdmin): +class DivisionAdmin(BaseAdmin): """Aдминка для Division.""" ordering = ("-updated_at",) - list_display = ("title", "author", "created_at", "updated_at", "courses") + list_display = ("title", "author", "updated_at", "courses") + exclude = ("author",) list_select_related = ("author",) @admin.display(description="Курсы") def courses(self, obj): - return [course.title for course in obj.course_set.all()] + """Показывает курсы по этим направлениям.""" + return [[course.title] for course in obj.course_set.all()] def get_queryset(self, request): - qs = self.model._default_manager.get_queryset().prefetch_related("course_set") - ordering = self.get_ordering(request) - if ordering: - qs = qs.order_by(*ordering) - return qs + return super().get_queryset(request).prefetch_related("course_set") + + def save_model(self, request, obj, form, change): + obj.author = request.user + obj.save() diff --git a/src/lizaalert/courses/models.py b/src/lizaalert/courses/models.py index cbf0f98a..29507824 100644 --- a/src/lizaalert/courses/models.py +++ b/src/lizaalert/courses/models.py @@ -596,6 +596,8 @@ def finish(self): class Division(TimeStampedModel): + """Модель направления курсов.""" + title = models.CharField(max_length=250, verbose_name="Название направления") description = models.CharField(max_length=1000, verbose_name="Описание направления") author = models.ForeignKey(User, on_delete=models.PROTECT, verbose_name="Создатель направления") diff --git a/src/lizaalert/users/admin.py b/src/lizaalert/users/admin.py index 8e894e10..3dae9e6b 100644 --- a/src/lizaalert/users/admin.py +++ b/src/lizaalert/users/admin.py @@ -9,6 +9,7 @@ Level, Location, User, + UserDivisionLevel, UserRole, Volunteer, VolunteerBadge, @@ -36,6 +37,11 @@ class LevelAdmin(admin.ModelAdmin): inlines = [VolunteerLevelInline] +class UserDivisionLevelInline(admin.TabularInline): + model = UserDivisionLevel + extra = 1 + + class BadgeAdminForm(forms.ModelForm): class Meta: model = Badge @@ -102,7 +108,17 @@ def clean(self): class VolunteerAdmin(admin.ModelAdmin): - inlines = [VolunteerLevelInline, VolunteerBadgeInline] + inlines = [VolunteerLevelInline, VolunteerBadgeInline, UserDivisionLevelInline] + + +class UserDivisionLevelAdmin(admin.ModelAdmin): + list_display = ("id", "volunteer", "division", "level") + list_display_links = ("volunteer",) + list_filter = ( + "volunteer", + "division", + "level", + ) admin.site.register(User, CustomUserAdmin) @@ -113,3 +129,4 @@ class VolunteerAdmin(admin.ModelAdmin): admin.site.register(Department) admin.site.register(Badge, BadgeAdmin) admin.site.register(Level, LevelAdmin) +admin.site.register(UserDivisionLevel, UserDivisionLevelAdmin) diff --git a/src/lizaalert/users/migrations/0010_auto_20240313_2336.py b/src/lizaalert/users/migrations/0010_auto_20240313_2336.py new file mode 100644 index 00000000..6d8a1a33 --- /dev/null +++ b/src/lizaalert/users/migrations/0010_auto_20240313_2336.py @@ -0,0 +1,38 @@ +# Generated by Django 3.2.23 on 2024-03-13 20:36 + +from django.db import migrations, models +import django.db.models.deletion + + +class Migration(migrations.Migration): + + dependencies = [ + ('courses', '0028_auto_20240313_1341'), + ('users', '0009_auto_20240313_1341'), + ] + + operations = [ + migrations.AlterField( + model_name='badge', + name='division', + field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, to='courses.division', verbose_name='Направление умения'), + ), + migrations.CreateModel( + name='UserDivisionLevel', + fields=[ + ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), + ('division', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='courses.division', verbose_name='Направление умения')), + ('level', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='users.level', verbose_name='Уровень умения')), + ('volunteer', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='division_level', to='users.volunteer', verbose_name='Волонтер')), + ], + options={ + 'verbose_name': 'Уровень волонтера по направлениям', + 'verbose_name_plural': 'Уровни волонтеров по направлениям', + }, + ), + migrations.AddField( + model_name='volunteer', + name='division_levels', + field=models.ManyToManyField(blank=True, related_name='volunteers', through='users.UserDivisionLevel', to='courses.Division', verbose_name='Уровень умения'), + ), + ] diff --git a/src/lizaalert/users/models.py b/src/lizaalert/users/models.py index e427392e..fbeb9148 100644 --- a/src/lizaalert/users/models.py +++ b/src/lizaalert/users/models.py @@ -164,7 +164,7 @@ class BadgeCategory(models.TextChoices): verbose_name="Курс для получения", ) division = models.ForeignKey( - "courses.Division", on_delete=models.PROTECT, verbose_name="Направление умения", null=True, blank=True + "courses.Division", on_delete=models.SET_NULL, verbose_name="Направление умения", null=True, blank=True ) class Meta: @@ -302,6 +302,13 @@ class Volunteer(models.Model): ) created_at = models.DateTimeField("Дата и время создания запси", auto_now_add=True) updated_at = models.DateTimeField("Дата обновления записи", auto_now=True) + division_levels = models.ManyToManyField( + "courses.Division", + through="users.UserDivisionLevel", + blank=True, + related_name="volunteers", + verbose_name="Уровень умения", + ) class Meta: db_table = "volunteers" @@ -327,3 +334,27 @@ def create_default_volunteer_level(sender, instance, created, **kwargs): if not existing_record: VolunteerLevel.objects.create(volunteer=volunteer, level=beginner_level, confirmed=True) + + +class UserDivisionLevel(models.Model): + """Модель для связи пользователей, направлений и уровней.""" + + volunteer = models.ForeignKey( + Volunteer, + on_delete=models.CASCADE, + related_name="division_level", + verbose_name="Волонтер", + ) + division = models.ForeignKey("courses.Division", on_delete=models.CASCADE, verbose_name="Направление умения") + level = models.ForeignKey( + Level, + on_delete=models.CASCADE, + verbose_name="Уровень умения", + ) + + class Meta: + verbose_name = "Уровень волонтера по направлениям" + verbose_name_plural = "Уровни волонтеров по направлениям" + + def __str__(self): + return f"Направление {self.division.title}"