仅允许已登录的用户对帖子发表评论

时间:2019-09-20 01:10:51

标签: django

提交表单时,我很难找到评论的作者

这对我的发布方法很好,对评论发表的意见不多

Models.py

    class Post(models.Model):
        title = models.CharField(max_length=100)#title of a post
        content = models.TextField()
        date_posted = models.DateTimeField(default=timezone.now)
        author = models.ForeignKey(User, on_delete=models.CASCADE) #if a user is deleted all of their post will be as well
        view_count = models.IntegerField(default=0)


    def __str__(self):
        return self.title

    def get_absolute_url(self):
        return reverse('post-detail', kwargs={'pk': self.pk})

class Comment(models.Model):
    post = models.ForeignKey('forum.Post', on_delete=models.CASCADE, related_name='comments')
    author = models.ForeignKey(User, on_delete=models.CASCADE)
    text = models.TextField(null=True)
    created_date = models.DateTimeField(default=timezone.now)


    def __str__(self):
        return self.text

    def get_absolute_url(self):
        return reverse('post-detail', kwargs={'pk': self.pk})

Views.py

class CommentCreate(LoginRequiredMixin,CreateView):
    model = Comment
    fields = ['text']

    def for_valid(self,form):
        form.instance.author = self.request.users
        return super().form_valid(form)

class PostCreate(LoginRequiredMixin, CreateView):
    model = Post
    fields = ['title', 'content']

    def form_valid(self,form):
        form.instance.author = self.request.user
        return super().form_valid(form)

class PostDetail(DetailView):
    model = Post


    def get_context_data(self, **kwargs):
        data = super(PostDetail, self).get_context_data(**kwargs)
        vc = self.object.view_count
        self.object.view_count = F('view_count') + 1
        self.object.save()
        self.object.view_count = vc + 1
        return data

Post_detail模板

{% extends "forum/base.html" %}

{% block content %}
    <article class="media content-section">
      <div class="media-body">
        <div class="article-metadata">
          <a class="mr-2" href="#">{{ object.author }}</a>
          <small class="text-muted">{{ object.date_posted }}</small>
          <small class="text-muted">{{ object.view_count }}</small>
          {% if object.author == user %}
            <div>
              <a class="btn btn-secondary btn-sm mt-1 mb-1" href="{% url 'post-update' object.id %}">Update</a>
              <a class="btn btn-danger btn-sm mt-1 mb-1" href="{% url 'post-delete' object.id %}">Delete</a>
            </div>
          {% endif %}
        </div>
        <h2 class="article-title">{{ object.title }}</h2>
        <p class="article-content">{{ object.content }}</p>
        <a class="btn btn-default" href="{% url 'add_comment_to_post' pk=post.pk %}">Add comment</a>
        {% for comment in post.comments.all %}
          <div class="comment">
            <div class="date">{{ comment.created_date }}</div>
              <strong>{{ comment.author }}</strong>
              <p>{{ comment.text|linebreaks }}</p>
            </div>
            {% empty %}
            <p>No comments here yet :(</p>
            {% endfor %}
      </div>
    </article>
{% endblock content %}

我得到的错误是“ NOT NULL约束失败:forum_comment.author_id”。我不确定与我的帖子CreateView有什么区别

3 个答案:

答案 0 :(得分:0)

尝试使用 self.request.user ,而不是 self.request.users 。并将 for_valid 更改为 form_valid 。如果这样不起作用,请尝试类似的方法。 new_comment 是您可以在此处保存并从函数返回的实例,而不是表单

CommentCreate 类的 form_valid 函数中

     new_post = form.save(commit=False)
     new_post.author = self.request.user
     new_post.save()
     return new_post

PostCreate 类的 form_valid 函数内部:

     new_comment = form.save(commit=False)
     new_comment.author = self.request.user
     new_comment.post = super().form_valid(form)         
     new_comment.save()
     return new_comment 

答案 1 :(得分:0)

您有两个错字

for_valid应该是form_valid

def form_valid(self,form):
        form.instance.author = self.request.users
        return super().form_valid(form)

self.request.users应该是self.request.user

答案 2 :(得分:0)

在应用程序内的ModelForm文件中为Comment创建一个forms.py

# your_app/forms.py

from django import forms
from .models import Comment

class CommentModelForm(forms.ModelForm):
    class Meta:
        model = Comment
        fields = ['post', 'text']
        widgets = {
            'post': forms.HiddenInput(),
            'text': forms.Textarea(attrs={'placeholder': 'Write your comment here...'}),
        }

在那之后编辑您的PostDetail视图,以便您可以将CommentModelForm实例与post实例一起设置为以下格式:

class PostDetail(DetailView):
    model = Post

    def get_context_data(self, **kwargs):
        data = super(PostDetail, self).get_context_data(**kwargs)
        vc = self.object.view_count
        self.object.view_count = F('view_count') + 1
        self.object.save()
        self.object.view_count = vc + 1
        initial_comment_data = {
            'post': self.object,
        }
        data['comment_form'] = CommentModelForm(initial=initial_comment_data)
        return data

CommentModelForm添加到您的CommentCreate视图中:

class CommentCreate(LoginRequiredMixin,CreateView):
    model = Comment
    form_class = CommentModelForm

    def form_valid(self,form):
        form.instance.author = self.request.user
        return super().form_valid(form)

最后,您的PostDetail的模板应如下所示:

# your_app/templates/your_app/post_detail.html

...
<form method="POST" action="{% url 'yourapp:comment-create' %}">
  {% csrf_token %}
  {{ comment_form }}
  <button type="submit">Place a comment</button>
</form>
<div>
  {% for comment in post.comments.all %}
    <p>{{ comment.text }} - by {{ comment.author }} at {{ comment.created_date }}</p>
  {% empty %}
    <p>No comments yet. Be the first one!</p>
  {% endfor %}
</div>