如何在 JavaScript 和 Django 中正确使用 Fetch?
How to correctly use Fetch in JavaScript and Django?
我正在尝试制作一个 METAR 解码器,如图所示:
我在 Vanilla js 中使用 fetch
,我打算将输入的代码发送到 Django 视图。从 Django 视图中,解码后的数据将被提取并显示在模板中。
views.py
def ToolsPageView(request):
if request.method == "POST":
jsonData = json.loads(request.body)
metarCode = jsonData.get('Metar')
return JsonResponse("Success", safe=False)
return render(request, 'app/tools.html')
urls.py
...
path("tools", views.ToolsPageView, name="tools")
tools.html
<div class="metar-code-decode">
<form method="POST" action="{% url 'tools' %}" id="metar-form">
{% csrf_token %}
<input type="text" placeholder="Enter METAR: " id="metar-value"> <br>
<input type="submit" id="metar-button">
</form>
</div>
tool.js
function getDecodedMetar() {
let formButton = document.querySelector("#metar-button");
formButton.onclick = function (e) {
let metarCode = document.querySelector("#metar-value").value;
sendMetar(metarCode);
//e.preventDefault();
//getMetar(metarCode);
};
}
function sendMetar(metarCode) {
fetch('/tools', {
method: "POST",
headers: {
"X-CSRFToken": getCookie("csrftoken"),
},
body: JSON.stringify({
Metar: metarCode,
}),
});
}
我在 POST
中使用了相同的代码,在 fetch
中我不得不让用户更新 his/her 配置文件。这奏效了。但是,这不起作用,并且在重新启动服务器后错误不断变化。第一次尝试时,没有产生任何错误,服务器还显示正在发出 POST
请求。我得到的最新错误是“为了允许序列化非字典对象,将安全参数设置为 False”。即使在 JsonResponse()
中设置 safe=False
之后,我也一次又一次地得到同样的结果。值得注意的是,request
转换为 request.json()
时会出错。
我是不是用错了fetch
?如果是,正确的做法是什么?
我不确定你的流程是否正确。这个想法是,单击按钮时,将调用一个函数(获取),该函数将数据发送到视图,视图将对其进行解码并将其发送回 JavaScript,以便可以显示 [=18] =]无需重新加载整个页面。
我认为这可能有帮助:
let formButton = document.querySelector("#metar-button");
// When the button is clicked,
formButton.onClick = function(e) {
// do NOT send the form the usual way
e.preventDefault();
let metarCode = document.querySelector("#metar-value").value;
// Run the function that will send the code to the ToolsPageView
sendMetar(metarCode);
}
async function sendMetar(metarCode) {
const response = await fetch('/tools', {
method: "POST",
headers: {
"X-CSRFToken": getCookie("csrftoken"),
},
body: JSON.stringify({
'Metar': metarCode,
}),
})
.then(response => response.json())
.then(data => {
console.log(data);
// extract the decoded value from the data sent back from the view
// display it by targeting the element in your html that you want
// to display it
});
}
在您看来,
def ToolsPageView(request):
if request.method == "POST":
jsonData = json.loads(request.body)
metarCode = jsonData.get('Metar')
# Remove the original JsonResponse
# return JsonResponse("Success", safe=False)
# and INSTEAD,
# Send the code back to the JavaScript
# I don't THINK you need safe=False here?
return JsonResponse({'MetarCode': metarCode})
return render(request, 'app/tools.html')
我正在尝试制作一个 METAR 解码器,如图所示:
我在 Vanilla js 中使用 fetch
,我打算将输入的代码发送到 Django 视图。从 Django 视图中,解码后的数据将被提取并显示在模板中。
views.py
def ToolsPageView(request):
if request.method == "POST":
jsonData = json.loads(request.body)
metarCode = jsonData.get('Metar')
return JsonResponse("Success", safe=False)
return render(request, 'app/tools.html')
urls.py
...
path("tools", views.ToolsPageView, name="tools")
tools.html
<div class="metar-code-decode">
<form method="POST" action="{% url 'tools' %}" id="metar-form">
{% csrf_token %}
<input type="text" placeholder="Enter METAR: " id="metar-value"> <br>
<input type="submit" id="metar-button">
</form>
</div>
tool.js
function getDecodedMetar() {
let formButton = document.querySelector("#metar-button");
formButton.onclick = function (e) {
let metarCode = document.querySelector("#metar-value").value;
sendMetar(metarCode);
//e.preventDefault();
//getMetar(metarCode);
};
}
function sendMetar(metarCode) {
fetch('/tools', {
method: "POST",
headers: {
"X-CSRFToken": getCookie("csrftoken"),
},
body: JSON.stringify({
Metar: metarCode,
}),
});
}
我在 POST
中使用了相同的代码,在 fetch
中我不得不让用户更新 his/her 配置文件。这奏效了。但是,这不起作用,并且在重新启动服务器后错误不断变化。第一次尝试时,没有产生任何错误,服务器还显示正在发出 POST
请求。我得到的最新错误是“为了允许序列化非字典对象,将安全参数设置为 False”。即使在 JsonResponse()
中设置 safe=False
之后,我也一次又一次地得到同样的结果。值得注意的是,request
转换为 request.json()
时会出错。
我是不是用错了fetch
?如果是,正确的做法是什么?
我不确定你的流程是否正确。这个想法是,单击按钮时,将调用一个函数(获取),该函数将数据发送到视图,视图将对其进行解码并将其发送回 JavaScript,以便可以显示 [=18] =]无需重新加载整个页面。
我认为这可能有帮助:
let formButton = document.querySelector("#metar-button");
// When the button is clicked,
formButton.onClick = function(e) {
// do NOT send the form the usual way
e.preventDefault();
let metarCode = document.querySelector("#metar-value").value;
// Run the function that will send the code to the ToolsPageView
sendMetar(metarCode);
}
async function sendMetar(metarCode) {
const response = await fetch('/tools', {
method: "POST",
headers: {
"X-CSRFToken": getCookie("csrftoken"),
},
body: JSON.stringify({
'Metar': metarCode,
}),
})
.then(response => response.json())
.then(data => {
console.log(data);
// extract the decoded value from the data sent back from the view
// display it by targeting the element in your html that you want
// to display it
});
}
在您看来,
def ToolsPageView(request):
if request.method == "POST":
jsonData = json.loads(request.body)
metarCode = jsonData.get('Metar')
# Remove the original JsonResponse
# return JsonResponse("Success", safe=False)
# and INSTEAD,
# Send the code back to the JavaScript
# I don't THINK you need safe=False here?
return JsonResponse({'MetarCode': metarCode})
return render(request, 'app/tools.html')