Шаблон home. html имеет 'like-section' в качестве идентификатора, но ваш селектор JQuery получает $ ('# like-section {{post.id}}') - отсутствие post.id в шаблоне может быть причина, по которой обновляется только первое сообщение.
<div class="ml-1" id="like-section">
{% include 'ajax_postlikes.html' %}
</div>
Редактировать: Итак, я воссоздаю ваши виды, модели и т. д. c. и удалось заставить его работать с некоторыми изменениями.
- Я изменил дом. Шаблон html, чтобы включить Django язык шаблонов для l oop, я не мог видеть это в вашем исходном коде, поэтому не уверен, как сообщения создаются в шаблоне точно. Этот формат будет работать при загрузке страницы и при вызове AJAX для одного лайка. Я также внес некоторые изменения в вызов AJAX и, как обрабатывается ответ, я заметил какой-то случайный язык шаблонов, который не будет работать.
<body>
<div class="ml-1" id="like-section">
{% for post in post_list %}
{% include 'ajax_postlikes.html' %}
{% endfor %}
</div>
<script type="text/javascript">
$(document).on('click', '.like', function(event){
event.preventDefault();
var pk = $(this).attr('value');
$.ajax({
type: 'POST',
url: "{% url 'like_post_view' %}",
headers: { 'X-CSRFToken': $('input[name=csrfmiddlewaretoken]').val() },
data: {id: pk},
success: function(response) {
$('#like-section'+pk).html(response)
},
error: function(rs, e) {
console.log(rs.responseText);
},
});
});
</script>
</body>
Я также изменил формат ajax_postlikes. html, я думаю, вы уже сделали это, но я добавил идентификатор в форму. Я также изменил работу оператора if / else, который объясняется в представлении.
<form id='like-section{{ post.id }}' action="{% url 'like_post_view' %}" method="POST">
{% csrf_token %}
{% if post.liked_by_user %}
<button type="submit" name="post_id" value="{{ post.id }}" class="like float-left mr-2">
Unlike
</button>
{% else %}
<button type="submit" name="post_id" value="{{ post.id }}" class="like float-left mr-2">
Like
</button>
{% endif %}
</form>
Это домашний вид в views.py - вместо того, чтобы иметь переменную для is_liked и разделять их, вы можете добавить переменную к объекту QuerySet, на которую затем можно ссылаться в шаблоне (показано выше).
def home_view(request):
posts = Post.objects.all()
for post in posts:
print(post)
print(post.likes.filter(user=request.user).exists())
if post.likes.filter(user=request.user).exists():
post.liked_by_user = True
else:
post.liked_by_user = False
context = {'post_list': posts}
return render(request, 'home.html' , context)
Наконец, я обновил представление AJAX в том же ключе.
def like_post_view(request):
post = get_object_or_404(Post, id=request.POST.get('id'))
if post.likes.filter(user=request.user).exists():
Like.objects.filter(post=post,user=request.user).delete()
post.liked_by_user = False
else:
Like.objects.create(post=post, user=request.user)
post.liked_by_user = True
context = {'post': post}
if request.is_ajax():
return render(request, 'ajax_postlike.html', context)
return HttpResponseRedirect(request.META.get('HTTP_REFERER'))
Это работает для меня и обновляет кнопку (то есть форму) при каждом нажатии. Я понимаю, что я удалил некоторые ваши логи фильтрации и других моделей c, но это должно быть легко добавить обратно.