I have been working on a like/unlike function on my django project in which a user can like like a post and if so the user can dislike it like in instagram. Now to finish with this part of the project I need to make the not refresh the page when a like or unlike button is pressed but the problem is that I am very very new to ajax. How can I acomplish this?
models.py
class Post(models.Model):
text = models.CharField(max_length=200)
user = models.ForeignKey(User, related_name='imageuser', on_delete=models.CASCADE, default='username')
liked = models.ManyToManyField(User, default=None, blank=True, related_name='liked')
updated = models.DateTimeField(auto_now=True)
created =models.DateTimeField(auto_now_add=True)
def __str__(self):
return str(self.text)
def get_absolute_url(self):
return reverse('comments', args=[self.pk])
LIKE_CHOICES = (
('Like', 'Like'),
('Unlike', 'Unlike'),
)
class Like(models.Model):
author = models.ForeignKey(User, on_delete=models.CASCADE)
post = models.ForeignKey(Post, on_delete=models.CASCADE)
value = models.CharField(choices=LIKE_CHOICES, default='Like', max_length=10)
def __str__(self):
return str(self.post)
views.py
def like_post(request):
user = request.user
if request.method == 'POST':
post_id = request.POST.get('post_id')
post_obj = Post.objects.get(id=post_id)
if user in post_obj.liked.all():
post_obj.liked.remove(user)
else:
post_obj.liked.add(user)
like, created = Like.objects.get_or_create(author=user, post_id=post_id)
if not created:
if like.value == 'Like':
like.value == 'Unlike'
else:
like.value = 'Like'
like.save()
return redirect('home')
def home(request):
contents = Post.objects.all()
context = {
"contents": contents,
}
print("nice2")
return render(request, 'home.html', context)
urls.py
urlpatterns = [
path('', views.home, name='home'),
path('like/', views.like_post, name="like-post"),
]
home.html
<form action="{% url 'like-post' %}" method="POST">
{% csrf_token %}
<input type='hidden' name="post_id" value="{{ content.id }}">
{% if user not in content.liked.all %}
<button type="submit">Like</button>
{% else %}
<button type="submit">Unlike</button>
{% endif %}
</form>
<strong>{{ content.liked.all.count }}</strong>
2
Answers
To avoid updating the page, you can set the button on your html as:
Instead of using submit, you’ll have to add an event listener to the button or a function associated with the onclick so you can call the ajax to handle this request on the background.
You can also achieve that by providing a null action for you form, by using:
Take a look at this tutorial:
https://simpleisbetterthancomplex.com/tutorial/2016/08/29/how-to-work-with-ajax-request-with-django.html
This is related to the default html behavior of a button with
type=submit
inside a form tag. By default, if you click in the button with type submit, it tries to send your data and reload your page. You can just change the type of the button and let your javascript code deal with the button behavior. On each of your buttons, add:For the JavaScript code, just add to your tag or separate js file: