You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

168 lines
5.8 KiB

from django.contrib import admin
from django import forms
from django.utils.translation import gettext_lazy as _
from unfold.admin import ModelAdmin, StackedInline
from unfold.contrib.filters.admin import (
ChoicesDropdownFilter,
MultipleRelatedDropdownFilter,
RangeDateFilter,
)
from utils.admin import project_admin_site
from apps.course.models import (
CourseLiveSession,
LiveSessionRecording,
LiveSessionUser,
USER_ROLE_CHOICES,
RECORDING_TYPE_CHOICES,
)
from django.contrib.auth import get_user_model
User = get_user_model()
# --- WIDTH ENFORCEMENT & PLACEHOLDER TEXT FOR DROPDOWNS ---
class MinWidthInlineForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# Target the dropdown fields to ensure they don't collapse
target_dropdown_fields = ['user', 'role', 'recording_type']
for field_name, field in self.fields.items():
if field_name in target_dropdown_fields:
if hasattr(field.widget, 'attrs'):
existing_class = field.widget.attrs.get('class', '')
field.widget.attrs['class'] = f"{existing_class} min-w-[250px] w-full"
existing_style = field.widget.attrs.get('style', '')
field.widget.attrs['style'] = f"{existing_style} min-width: 250px; width: 250px;"
# 🔔 Add the custom placeholder text
if hasattr(field, 'empty_label'):
field.empty_label = _("Select a value")
class LiveSessionUserInline(StackedInline):
model = LiveSessionUser
form = MinWidthInlineForm
extra = 1
tab = True
fieldsets = (
(None, {
'fields': (('user', 'role', 'is_online'),) # Grouped horizontally
}),
(_("Timing"), {
'fields': (('entered_at', 'exited_at'),) # Grouped horizontally
}),
)
show_change_link = True
verbose_name = _("Session User")
verbose_name_plural = _("Session Users")
# 🔔 FILTER THE USER DROPDOWN TO ONLY SHOW ACTIVE & NON-GUEST USERS
def formfield_for_foreignkey(self, db_field, request, **kwargs):
if db_field.name == "user":
kwargs["queryset"] = User.objects.filter(is_active=True, email__isnull=False)
return super().formfield_for_foreignkey(db_field, request, **kwargs)
class LiveSessionRecordingInline(StackedInline):
model = LiveSessionRecording
form = MinWidthInlineForm
extra = 1
tab = True
fieldsets = (
(None, {
'fields': (('title', 'recording_type', 'is_active'),) # Grouped horizontally
}),
(_("Media"), {
'fields': ('file',)
}),
)
show_change_link = True
verbose_name = _("Session Recording")
verbose_name_plural = _("Session Recordings")
class CourseLiveSessionAdmin(ModelAdmin):
list_display = ("subject", "course", "started_at", "ended_at", "created_at")
list_filter = (
("course", MultipleRelatedDropdownFilter),
("started_at", RangeDateFilter),
)
search_fields = ("subject", "course__title")
ordering = ("-started_at",)
autocomplete_fields = ("course",)
readonly_fields = ("created_at", "updated_at")
# Add the custom tabs here
inlines = [LiveSessionUserInline, LiveSessionRecordingInline]
fieldsets = (
(None, {"fields": ("course", "subject", "started_at", "ended_at")}),
(_("Timestamps"), {"fields": ("created_at", "updated_at")}),
)
class LiveSessionUserAdmin(ModelAdmin):
list_display = ("user", "session", "role", "is_online", "entered_at", "exited_at")
list_filter = (
("session", MultipleRelatedDropdownFilter),
("user", MultipleRelatedDropdownFilter),
("role", ChoicesDropdownFilter),
("entered_at", RangeDateFilter),
("is_online", admin.BooleanFieldListFilter),
)
search_fields = (
"user__email",
"user__fullname",
"session__subject",
)
autocomplete_fields = ("user", "session")
readonly_fields = ("created_at", "updated_at")
fieldsets = (
(None, {"fields": ("session", "user", "role")}),
(_("Session Timing"), {"fields": ("entered_at", "exited_at", "is_online")}),
(_("Timestamps"), {"fields": ("created_at", "updated_at")}),
)
def get_role_choices(self, request):
return USER_ROLE_CHOICES
# 🔔 FILTER THE STANDALONE ADMIN FORM AS WELL JUST IN CASE
def formfield_for_foreignkey(self, db_field, request, **kwargs):
if db_field.name == "user":
kwargs["queryset"] = User.objects.filter(is_active=True, email__isnull=False)
return super().formfield_for_foreignkey(db_field, request, **kwargs)
class LiveSessionRecordingAdmin(ModelAdmin):
list_display = ("title", "session", "recording_type", "is_active", "created_at")
list_filter = (
("session", MultipleRelatedDropdownFilter),
("recording_type", ChoicesDropdownFilter),
("created_at", RangeDateFilter),
("is_active", admin.BooleanFieldListFilter),
)
search_fields = ("title", "session__subject", "session__course__title")
autocomplete_fields = ("session",)
readonly_fields = ("created_at", "updated_at")
fieldsets = (
(None, {"fields": ("session", "title", "recording_type")}),
(_("Files"), {"fields": ("file", "file_time", "thumbnail")}),
(_("Status"), {"fields": ("is_active",)}),
(_("Timestamps"), {"fields": ("created_at", "updated_at")}),
)
def get_recording_type_choices(self, request):
return RECORDING_TYPE_CHOICES
project_admin_site.register(CourseLiveSession, CourseLiveSessionAdmin)
project_admin_site.register(LiveSessionUser, LiveSessionUserAdmin)
project_admin_site.register(LiveSessionRecording, LiveSessionRecordingAdmin)