[英]Ajax not work in Django post
我正在嘗試在Django中使用ajax在新聞網站中發表評論,但是它不起作用。 當我單擊“提交”按鈕時,它仍然刷新頁面,沒有任何影響,就像沒有ajax一樣。
我真的是Django和Ajax的新手,有沒有朋友可以幫助我解決這個問題?
這是我的view.py:
def newsDetailView(request, news_pk):
news = News.objects.get(id=news_pk)
title = news.title
author = news.author_name
add_time = news.add_time
content = news.content
category = news.category
tags = news.tag.annotate(news_count=Count('news'))
all_comments = NewsComments.objects.filter(news=news)
comment_form = CommentForm(request.POST or None)
if request.method == 'POST' and comment_form.is_valid():
if not request.user.is_authenticated:
return render(request, 'login.html', {})
comments = comment_form.cleaned_data.get("comment")
news_comment = NewsComments(user=request.user, comments=comments, news=news)
news_comment.save()
return render(request, "news_detail.html", {
'title': title,
'author': author,
'add_time': add_time,
'content': content,
'tags': tags,
'category': category,
'all_comments': all_comments,
'comment_form': comment_form
})
這是我的news_detail模板,可在其中獲取表單數據:
{% if user.is_authenticated %}
<form id="js-pl-submit" method="POST" action="">{% csrf_token %}
{% for field in comment_form %}
{% for error in field.errors %}
<div class="alert alert-warning text-center mb-3" role="alert">{{ error }}</div>
{% endfor %}
{% endfor %}
在這里,我在news_detail模板中將所有注釋呈現到模板:
{% for user_comments in all_comments %}
<img class="mr-3 comment-avatar rounded-circle"src="{{ MEDIA_URL }}{{ user_comments.user.image }}"alt="Generic placeholder image">
<div class="media-body">
<h6 class="mt-0 mb-1">{{ user_comments.user.username }}</h6>
{{ user_comments.comments }}
</div>
<span>{{ user_comments.add_time }}</span>
{% endfor %}
這是我在news_detail模板中的Ajax:
$('#js-pl-submit').on('click', function(){
var comments = $("#js-pl-textarea").val()
if(comments == ""){
alert("評論不能為空")
return false
}
$.ajax({
cache: false,
type: "POST",
url:"",
data:{'news_pk':{{ news.id }}, 'comments':comments},
async: true,
beforeSend:function(xhr, settings){
xhr.setRequestHeader("X-CSRFToken", "{{ csrf_token }}");
},
success: function(data) {
if(data.status == 'fail'){
if(data.msg == '用戶未登錄'){
window.location.href="login";
}else{
alert(data.msg)
}
}else if(data.status == 'success'){
window.location.reload();//刷新當前頁面.
}
},
});
return false;
});
最后是我的評論的form.py。
def words_validator(comment):
if len(comment) < 4:
raise ValidationError("親,最少寫兩個字")
class CommentForm(forms.Form):
comment = forms.CharField(widget=forms.Textarea(), validators=[words_validator])
將點擊事件添加到不在form
上的button
上,您必須將其隱式更改為button
。 默認情況下, button
的類型為Submit。
<form method="POST" action="">
<button type="button" id="js-pl-submit">
刪除表格的id
。 提交按鈕提交表單數據並重新加載頁面。
您的綁定不正確,您在表單上具有單擊處理程序,應該將其作為提交處理程序。 如果將其綁定到按鈕,則可以使用單擊處理程序。
$('#js-pl-submit').on('submit', function(){//<-- here
var comments = $("#js-pl-textarea").val()
if(comments == ""){
alert("評論不能為空")
return false
}
$.ajax({
cache: false,
type: "POST",
url:"",
data:{'news_pk':{{ news.id }}, 'comments':comments},
async: true,
beforeSend:function(xhr, settings){
xhr.setRequestHeader("X-CSRFToken", "{{ csrf_token }}");
},
success: function(data) {
if(data.status == 'fail'){
if(data.msg == '用戶未登錄'){
window.location.href="login";
}else{
alert(data.msg)
}
}else if(data.status == 'success'){
window.location.reload();//刷新當前頁面.
}
},
});
return false;
});
這可能有效,它包含您的代碼中的一些建議。
++ newsDetailView
news_details.html中的++
腳本中的++
views.py
def newsDetailView(request, news_pk):
#news = News.objects.get(id=news_pk) No need to get the object like this anymore
news = get_object_or_404(News,id=news_pk) #
title = news.title
author = news.author_name
add_time = news.add_time
content = news.content
category = news.category
tags = news.tag.annotate(news_count=Count('news'))
comment_form = CommentForm(request.POST or None)
if request.method == 'POST' and comment_form.is_valid():
# if request.method == 'POST' and request.is_ajax() and comment_form.is_valid(): To make sure it's ajax
if not request.user.is_authenticated:
return JsonResponse({"msg":"You need to login",
"url":'login_url','status':'login_required'})
comments = comment_form.cleaned_data.get("comment")
news_comment = NewsComments(user=request.user, comments=comments, news=news)
news_comment.save()
# This needs to be after request.POST process
all_comments = NewsComments.objects.filter(news=news)
context = {
'title': title,
'author': author,
'add_time': add_time,
'content': content,
'tags': tags,
'category': category,
'all_comments': all_comments,
'comment_form': comment_form,
}
return render(request, "news_detail.html", context)
news_detail.html | 形成
{% if user.is_authenticated %}
<form id="js-pl-submit" method="POST" action="">{% csrf_token %}
{% for field in comment_form %}
{% for error in field.errors %}
<div class="alert alert-warning text-center mb-3" role="alert">{{ error }}</div>
{% endfor %}
{% endfor %}
</form>
{% endif %}
news_detail.html | 評論
<div id="comments_section">
{% for user_comments in all_comments %}
<img class="mr-3 comment-avatar rounded-circle" src="{{ MEDIA_URL }}{{ user_comments.user.image }}" alt="Generic placeholder image">
<div class="media-body">
<h6 class="mt-0 mb-1">{{ user_comments.user.username }}</h6>
{{ user_comments.comments }}
</div>
<span>{{ user_comments.add_time }}</span>
{% endfor %}
</div>
JS腳本
$(document).on('submit','#js-pl-submit',function(){ // Correction : Not click, but submit
var comments = $("#js-pl-textarea").val()
if(!comments){
alert("評論不能為空")
return false
}
$.ajax({
cache: false,
type: "POST",
url:"",
data:{
// 'news_pk':{{ news.id }}, No need to send the news.id
/// you are actually on the instance of `news` Object
'comments':comments,
'csrfmiddlewaretoken':$("input[name=csrfmiddlewaretoken]").val(), // retrieve `csrf_token` from `form`
},
async: true,
success: function(data) {
// Not sure it's the more powerful, but this should work like a charm
if(data.status == 'login_url'){
alert(data.msg);
window.location.href = data.url;
}
// Those 2 next lines are useful if you want to refresh without reload the page.
$("#js-pl-submit").replaceWith($('#js-pl-submit',data));//刷新當前頁面.
$("#comments_section").replaceWith($('#comments_section',data));
// This next line will reload the page
windows.location.reload();
},
error:function(){
// Codes here in case of error
},
statusCode:{
404:function(){
alert("Object not found");
},
500:function(){
alert("An error has occured on the server");
},
}
});
return false;
});
請隨時發表評論,以便我編輯我的答案,以幫助您成功。
最后,我做到了!感謝勛爵!非常興奮!請在此處查看我的詳細答案: Django Ajax Form錯誤地提交到另一個頁面,真的很感謝大家的回復!有了您的回復,我逐步弄清楚了這些問題!
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.