Django 创建 post
Django create post
我正在尝试创建一个新的 post 到论坛,它确实有效,我也在打印表格是否有效,但是当我去检查 post 是未 posted。在管理页面中,post 在那里,已批准,但缺少标签和类别字段。它们是在创建 post 时添加的,否则我会收到错误消息。但是我必须在管理页面中手动添加它们才能将 post posted 到论坛。
这是我的Post模型
class Post(models.Model):
title = models.CharField(max_length=400)
slug = models.SlugField(max_length=400, unique=True, blank=True)
user = models.ForeignKey(Author, on_delete=models.CASCADE)
content = HTMLField()
categories = models.ManyToManyField(Category)
date = models.DateTimeField(auto_now_add=True)
approved = models.BooleanField(default=True)
tags = TaggableManager()
comments = models.ManyToManyField(Comment, blank=True)
# closed = models.BooleanField(default=False)
# state = models.CharField(max_length=40, default="zero")
def save(self, *args, **kwargs):
if not self.slug:
self.slug = slugify(self.title)
super(Post, self).save(*args, **kwargs)
def __str__(self):
return self.title
这是我的views.py
@login_required
def create_post(request):
context = {}
form = PostForm(request.POST or None)
if request.method == "POST":
if form.is_valid():
print("\n\n form is valid")
author = Author.objects.get(user=request.user)
new_post = form.save(commit=False)
new_post.user = author
new_post.save()
return redirect('forums')
context.update({
'form': form,
'title': 'Create New Post'
})
return render(request, 'forums/create_post.html', context)
这个html就很简单了,测试一下。
<form method="POST">
{% csrf_token %}
{{form|crispy}}
<!-- Submit Post -->
<input type="submit" value="Save">
</form>
如有任何帮助,我们将不胜感激
行,new_post = form.save(commit=False)
不会根据docs保存多对多关系。解决方法
new_post = form.save(commit=False)
new_post.user = author
new_post.save()
form.save_m2m()
摘自docs
Another side effect of using commit=False is seen when your model has
a many-to-many relation with another model. If your model has a
many-to-many relation and you specify commit=False when you save a
form, Django cannot immediately save the form data for the
many-to-many relation. This is because it isn’t possible to save
many-to-many data for an instance until the instance exists in the
database.
To work around this problem, every time you save a form using
commit=False, Django adds a save_m2m() method to your ModelForm
subclass. After you’ve manually saved the instance produced by the
form, you can invoke save_m2m() to save the many-to-many form data.
我认为这并不能解决所有问题,但请尝试一下。
在commit=False
时,ModelForm
无法保存多对多关系的原因是因为它没有在数据库端创建Post
,因此没有可用于添加多对多关系的主键。
您可以使用 .save_m2m()
在保存了包装在表单中的实例后保存多对多关系,但也许更优雅的解决方案是将 request.user
附加到包装的实例在表单中,然后保存表单,从那时起,表单将在同一个函数调用中保存多对多关系,所以:
from django.shortcuts import get_object_or_404
# …
if form.is_valid():
form<strong>.instance.user =</strong> get_object_or_404(Author, user=request.user)
form<strong>.save()</strong>
可能值得将 .user
字段重命名为 .author
,因为现在它暗示它正在存储一个 User
对象,而不是 Author
对象。
我正在尝试创建一个新的 post 到论坛,它确实有效,我也在打印表格是否有效,但是当我去检查 post 是未 posted。在管理页面中,post 在那里,已批准,但缺少标签和类别字段。它们是在创建 post 时添加的,否则我会收到错误消息。但是我必须在管理页面中手动添加它们才能将 post posted 到论坛。
这是我的Post模型
class Post(models.Model):
title = models.CharField(max_length=400)
slug = models.SlugField(max_length=400, unique=True, blank=True)
user = models.ForeignKey(Author, on_delete=models.CASCADE)
content = HTMLField()
categories = models.ManyToManyField(Category)
date = models.DateTimeField(auto_now_add=True)
approved = models.BooleanField(default=True)
tags = TaggableManager()
comments = models.ManyToManyField(Comment, blank=True)
# closed = models.BooleanField(default=False)
# state = models.CharField(max_length=40, default="zero")
def save(self, *args, **kwargs):
if not self.slug:
self.slug = slugify(self.title)
super(Post, self).save(*args, **kwargs)
def __str__(self):
return self.title
这是我的views.py
@login_required
def create_post(request):
context = {}
form = PostForm(request.POST or None)
if request.method == "POST":
if form.is_valid():
print("\n\n form is valid")
author = Author.objects.get(user=request.user)
new_post = form.save(commit=False)
new_post.user = author
new_post.save()
return redirect('forums')
context.update({
'form': form,
'title': 'Create New Post'
})
return render(request, 'forums/create_post.html', context)
这个html就很简单了,测试一下。
<form method="POST">
{% csrf_token %}
{{form|crispy}}
<!-- Submit Post -->
<input type="submit" value="Save">
</form>
如有任何帮助,我们将不胜感激
行,new_post = form.save(commit=False)
不会根据docs保存多对多关系。解决方法
new_post = form.save(commit=False)
new_post.user = author
new_post.save()
form.save_m2m()
摘自docs
Another side effect of using commit=False is seen when your model has a many-to-many relation with another model. If your model has a many-to-many relation and you specify commit=False when you save a form, Django cannot immediately save the form data for the many-to-many relation. This is because it isn’t possible to save many-to-many data for an instance until the instance exists in the database.
To work around this problem, every time you save a form using commit=False, Django adds a save_m2m() method to your ModelForm subclass. After you’ve manually saved the instance produced by the form, you can invoke save_m2m() to save the many-to-many form data.
我认为这并不能解决所有问题,但请尝试一下。
在commit=False
时,ModelForm
无法保存多对多关系的原因是因为它没有在数据库端创建Post
,因此没有可用于添加多对多关系的主键。
您可以使用 .save_m2m()
在保存了包装在表单中的实例后保存多对多关系,但也许更优雅的解决方案是将 request.user
附加到包装的实例在表单中,然后保存表单,从那时起,表单将在同一个函数调用中保存多对多关系,所以:
from django.shortcuts import get_object_or_404
# …
if form.is_valid():
form<strong>.instance.user =</strong> get_object_or_404(Author, user=request.user)
form<strong>.save()</strong>
可能值得将 .user
字段重命名为 .author
,因为现在它暗示它正在存储一个 User
对象,而不是 Author
对象。