I am a beginner to django programming. I have been trying to add a like button to the post which is posted by the user.
In my models.py
class Post(models.Model):
post = models.CharField(max_length=500)
user = models.ForeignKey(User)
created = models.DateTimeField(auto_now_add=True)
updated = models.DateTimeField(auto_now=True)
Please help in adding a like button to my blog.
It's basic database structure, you can simply use a many to many field where you store every user that has liked/upvoted the post :
class Post(models.Model):
post = models.CharField(max_length=500)
user = models.ForeignKey(User)
created = models.DateTimeField(auto_now_add=True)
updated = models.DateTimeField(auto_now=True)
upvoted = models.ManyToManyField(User)
Related
I am trying to make a button on the post that when a user cliks on it, is requesting to be added to the post as an attendance and then, the author of the post has to approve that request.
Models.py
class Attending(models.Model):
is_approved = models.BooleanField(default=False)
attending = models.ManyToManyField(User, related_name='user_event_attending')
class Post(models.Model):
title = models.CharField(max_length=100)
content = models.TextField(blank=True)
date_posted = models.DateTimeField(default=timezone.now)
author = models.ForeignKey(User, on_delete=models.CASCADE)
attending = models.ForeignKey(Attending, on_delete=models.CASCADE, verbose_name='atending', null=True)
My problem here is that every time I writte a query for the button is giving me erros and I couldn`t figure it out how to get the reverse of the foreign key.
This is my code on my views.py
def request_event(request, pk):
previous = request.META.get('HTTP_REFERER')
try:
query = Attending.objects.get(pk=pk)
request_attending = query.post_set.add(request.user)
messages.success(request, f'Request sent!')
return redirect(previous)
except query.DoesNotExist:
return redirect('/')
Thank you very much for your help in advance!
This: query.post_set is just relationship. You cannot call method add just like that. You can add to ManyToMany relation and I believe you want to add user to Attending.attending field, not directly to Post object. Change that to:
...
query = Attending.objects.get(pk=pk)
query.attending.add(request.user)
messages.success(request, f'Request sent!')
....
| Update |
I think you should consider rearraning your relationships. If I understand your plan, you should go this way:
class Attending(models.Model):
...
attendant = models.ForeignKey(User, related_name='events_attending', on_delete=models.CASCADE)
post = models.ForeignKey('Post', on_delete=models.CASCADE)
class Post(models.Model):
...
author = models.ForeignKey(User, on_delete=models.CASCADE)
For one Post object there can be many Attending objects, then you can use relations like that:
att = Attending.objects.first()
att.post # get related Post object from ForeignKey | there is only one
post = Post.objects.first()
post.attending_set.all() # get all related Attending objects
Post.objects.get(attending=att) # get Post object that the Attending object have in ForeignKey field
user = User.objects.first()
user.post_set.all() # get all Post objects that User is author in
user.events_attending.all() # get all related Attending objects
For more check Django Docs.
Can't figure out where my mistake is. Not able to map through to display the list of blog comments. I'm using Django and react. From the code below, I tried to assess each blog post with comments using foreign key. But I'm not able to get the comment property from the blog. If I do something like {blog.title} I get the title of the blog back on the browser. Since comments are associated with each post I try to get different properties of comment from the blog object (just as I specified in the code below) but the value I'm getting is undefined. And have the following blog post and blog comment models:
class BlogComment(models.Model):
post = models.ForeignKey(BlogPost, on_delete=models.SET_NULL, related_name="post_comment", null=True)
user = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.SET_NULL, related_name="user_comment", null=True)
name = models.CharField(max_length=200, null=True, blank=True)
comment = models.TextField(null=True, blank=True)
dateCreated = models.DateTimeField(auto_now_add=True)
def __str__(self):
return str(self.user.username)
class BlogPost(models.Model):
...
author = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, on_delete=models.CASCADE)
body = models.TextField()
dateCreated = models.DateTimeField(auto_now_add=True)
And the serializers for both models are:
class CommentSerializer(serializers.ModelSerializer):
class Meta:
model = BlogComment
fields = '__all__'
class BlogPostSerializer(serializers.ModelSerializer):
comments = serializers.SerializerMethodField(read_only=True)
class Meta:
model = BlogPost
fields = "__all__"
def get_comments(self, obj):
comments = obj.comment_set.all()
serializer = CommentSerializer(comments, many=True)
return serializer.data
The endpint of comment is path('posts/<str:pk>/comment/', CreateCommentView, name="create-comment"),.
The endpoint is working. I'm able to add comment to posts both from the front end. The error comes when I try to map through the
comments for each post. Get the error: AttributeError: 'BlogPost' object has no attribute 'comment_set'.
Here is the code I'm using to map through to display all the blogs of a particular post in the blog details page in react. I'm assess each blog there:
<h2>{blog.title}</h2>
<img src={blog.image} />
<div variant='flush'>
{blog.comments.map((comment) => (
<div key={comment.id}>
<strong>{comment.name}</strong>
<p>{comment.dateCreated}</p>
<p>{comment.comment}</p>
</div>
))}
</div>
Here is the code I'm using to map through to display all the blogs of a particular post in the blog details page in react. If I do not map the error does not come up and I'm able to add comment. However, in order to display the comments under each blog post I map through. How do I fix this?
You need to use post_comment:
comments = obj.post_comment.all()
You declared it here:
post = models.ForeignKey(BlogPost, on_delete=models.SET_NULL, related_name="post_comment", null=True)
related_name is used as a name for Django relation. See more here.
But changing post_comment with something else would be a better solution for me.
I have 3 models as follows:
class Topic(models.Model):
title = models.CharField(max_length=128)
created = models.DateTimeField(auto_now_add=True)
class Thread(models.Model):
topic = models.ForeignKey(Topic, on_delete=models.CASCADE)
description = models.TextField()
created = models.DateTimeField(auto_now_add=True)
class Message(models.Model):
thread = models.ForeignKey(Thread, on_delete=models.CASCADE)
text = models.TextField()
created = models.DateTimeField(auto_now_add=True)
I want to get:
1- most active topics in this week by number of new messages
2- most active topics by most recent messages
Note: I have solved this challenge by getting the QuerySet and sorting it with python code. I want to know if there is a way to do the same with django ORM.
i have some fields in my django models.
class Product(models.Model):
user=models.ForeignKey(User)
product_name = models.CharField(max_length=50)
product_cost = models.IntegerField(default=0,null=True, blank=True)
product_description = models.TextField(null=True, blank=True)
quantity = models.IntegerField(default=0,null=True, blank=True)
product_image = models.FileField(upload_to='images/',blank=True,null=True,)
coupon_code = models.CharField(max_length=50)
time = models.DateTimeField(default=timezone.now)
def __str__(self):
return self.product_name or u''
when i use form to save all the data from front end in my database i can do this.
class DocumentForm(forms.ModelForm):
class Meta:
model = Product
fields = ('user','product_name','product_image','product_cost','product_description','product_description','coupon_code')
Problem is this i don't want to allow user to fill user data from front-end.when user save data it save request.user to user.
I am new to work with forms so facing some issues.
Please help me how can i do this.
Thanks in advance.
In fields you have to remove user:
so it will look like this:
class DocumentForm(forms.ModelForm):
class Meta:
model = Product
fields = ('product_name','product_image','product_cost','product_description','product_description','coupon_code')
and in your views.py when you save the data from the form you have write something like this:
user = request.user
in this case user will be saved if he is authenticated.
If you want that not authenticated user could fill the form too, you have to change in your model.py Product class from:
user=models.ForeignKey(User)
to:
user=models.ForeignKey(User, null=True)
then not authenticated user will be NULL.
I have two apps news and article which both have exactly the same model name Comment:
class Comment(models.Model):
author = models.ForeignKey(User)
created = models.DateTimeField(auto_now_add=True)
title = models.CharField(max_length=100, default='', blank=True)
body = models.TextField()
post = models.ForeignKey(Photo)
published = models.BooleanField(default=True)
Now, in a view I want to delete certain comments from both apps:
Comment.objects.filter(author=someauthor).delete()
How can I achieve that without changing the model names?
You can use import ... as ... so that both model names do not conflict:
from news.models import Comment as NewsComment
from article.models import Comment as ArticleComment
...
NewsComment.objects.filter(author=someauthor).delete()
ArticleComment.objects.filter(author=someauthor).delete()