Django Admin中如何通过related_name查看管理多对多关联对象
实现方案
核心是利用Django Admin的内联(Inline)机制,在User模型的编辑页嵌入关联课程的管理模块,不需要修改原有模型,只需要调整admin.py配置即可。
具体实现代码
直接在对应app的admin.py中添加如下配置:
from django.contrib import admin from django.contrib.auth.admin import UserAdmin as BaseUserAdmin from .models import User, Course # 授课课程内联:对应用户作为教师关联的课程(外键teacher字段) class TeacherCoursesInline(admin.TabularInline): model = Course fk_name = "teacher" # 必须指定,避免和多对多学生关联冲突 extra = 1 # 默认展示1个空白行用于快速新增课程 fields = ("name",) # 替换为你Course模型实际需要展示的字段,如标题、简介等 verbose_name = "授课课程" verbose_name_plural = "授课课程列表" # 可选:禁止在用户页直接删除课程,避免误操作,需要的话取消注释 # can_delete = False # 选课列表内联:对应用户作为学生关联的课程(多对多students字段) class StudentCoursesInline(admin.TabularInline): model = Course.students.through # 调用多对多关系自动生成的中间表 fk_name = "user" # 指定中间表中关联User的外键字段 extra = 1 verbose_name = "所选课程" verbose_name_plural = "选课列表" # 自定义User管理类,保留Django原生UserAdmin的全部原有功能 class UserAdmin(BaseUserAdmin): inlines = [TeacherCoursesInline, StudentCoursesInline] # 可选:在用户列表页增加授课数、选课数字段 list_display = BaseUserAdmin.list_display + ("count_teacher_courses", "count_student_courses") def count_teacher_courses(self, obj): return obj.teacher_courses.count() count_teacher_courses.short_description = "授课数量" def count_student_courses(self, obj): return obj.student_courses.count() count_student_courses.short_description = "选课数量" # 注册自定义User模型 try: admin.site.unregister(User) except admin.sites.NotRegistered: pass admin.site.register(User, UserAdmin) # Course模型的原有Admin配置可保留,无需修改 @admin.register(Course) class CourseAdmin(admin.ModelAdmin): list_display = ("name", "teacher") filter_horizontal = ("students",)
效果说明
配置完成后进入任意用户的Admin编辑页,页面底部会分两个区块展示关联课程:
- 授课课程区块:以紧凑表格形式展示该用户作为老师教授的所有课程,支持直接新增课程、编辑课程字段,点击课程名可跳转至课程详情页查看完整信息。如果开启了删除权限,勾选条目删除会同步删除对应课程记录(符合模型里
on_delete=models.CASCADE的级联规则)。 - 所选课程区块:展示该用户作为学生选中的所有课程,支持下拉选择新增课程关联,勾选条目删除只会移除用户和课程的选课关系,不会删除课程本身。
可选调整
- 如果觉得表格形式太拥挤,可以把
TabularInline换成StackedInline,每个课程条目会以独立块展示,适合Course字段较多的场景。 - 如果你的
students多对多字段用了自定义中间表,只需要把StudentCoursesInline的model参数替换成你自定义的中间表,fk_name换成中间表里指向User的字段名即可。 - 两个内联类的
fields属性可以根据需求自由增减字段,控制在用户页展示的课程信息维度。
内容的提问来源于stack exchange,提问作者ParsaAi
相关产品推荐
相关产品推荐

