Django 2.0中如何在Chapter的CreateView传递Course的pk值
解决Django 2.0中Chapter CreateView传递Course参数的问题
我来帮你搞定这个需求——要在创建Chapter时自动关联指定的Course,不用用户手动选择,对吧?咱们一步步来:
1. 先修正urls.py里的小错误
你提供的urls里最后一行的视图名写错了,应该是NewChapter.as_view(),修正后的完整urls.py:
from django.urls import path from courses.views import Courses, NewCourse, CourseView, NewChapter app_name = 'course' urlpatterns = [ path('all', Courses.as_view(), name='list'), path('new', NewCourse.as_view(), name='new'), path('<pk>/detail', CourseView.as_view(), name='detail'), path('<course_id>/chapter/add', NewChapter.as_view(), name='new_chapter'), ]
2. 调整NewChapter视图类
核心思路是从URL的course_id参数中拿到对应Course,然后在保存Chapter时自动关联。这里推荐重写form_valid方法(比用初始值更安全,避免用户篡改):
# courses/views.py from django.views.generic.edit import CreateView from django.shortcuts import get_object_or_404 from django.urls import reverse from .models import Chapter, Course class NewChapter(CreateView): model = Chapter # 这里只列出需要用户填写的字段,不要包含course fields = ['title', 'content'] # 替换成你实际的字段 template_name = 'courses/new_chapter.html' # 你的模板路径 def form_valid(self, form): # 从URL参数中获取course_id,找到对应的Course对象 course = get_object_or_404(Course, pk=self.kwargs['course_id']) # 把Course关联到当前要创建的Chapter实例 form.instance.course = course # 调用父类的form_valid完成保存 return super().form_valid(form) def get_success_url(self): # 保存成功后跳回对应的课程详情页,更友好 return reverse('course:detail', kwargs={'pk': self.kwargs['course_id']})
3. 模板调整(可选)
因为我们已经在视图里自动设置了Course,所以模板里不需要渲染course字段。你的表单模板可以直接这样写:
<!-- courses/templates/courses/new_chapter.html --> <h1>添加新章节</h1> <form method="post"> {% csrf_token %} {{ form.as_p }} <button type="submit">保存章节</button> </form>
如果你的Chapter模型里course字段是必填的,不用担心——因为我们在视图里已经提前设置好了,表单验证会通过。
额外提示
- 用
get_object_or_404可以避免用户输入不存在的course_id时出现错误页面,返回404更合理 - 如果需要在模板里显示当前关联的课程名称,可以在视图里重写
get_context_data把Course对象传到模板:
def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) context['course'] = get_object_or_404(Course, pk=self.kwargs['course_id']) return context
然后模板里就能用{{ course.name }}显示课程名了。
内容的提问来源于stack exchange,提问作者Anuj TBE
相关产品推荐
相关产品推荐

