使用Fetch API将JSON对象发送到Flask服务器会导致400 Bad Request。

huangapple go评论119阅读模式
英文:

Sending A Json object through Fetch API to a Flask Server leads to a 400 Bad Request

问题

我尝试发送一些JSON数据到服务器,按照一些在线文章和官方的Flask文档,但我一直收到400错误。到目前为止,我尝试过的方法都没有成功。

我了解到,如果Flask没有正确格式化的JSON数据,它会引发此错误,还有一个要求的请求必须指定Content-Type标头为application/json,否则会发生相同的情况。

我复制了一些官方文档中的代码,以下是我到目前为止的代码:

在我的Flask应用程序中的视图函数:

  1. @main.route('/test', methods=['GET','POST'])
  2. def test():
  3. if request.method == 'POST':
  4. print(request.method)
  5. print(request.headers.get('Content-Type'))
  6. print(request.is_json)
  7. # 运行时会导致400错误
  8. #print(request.json)
  9. return render_template('test.html')

在test.html中的以下脚本标签:

  1. <script>
  2. let data = {"data": "Hello World!"}
  3. document.querySelector('#main').addEventListener('click', function () {
  4. fetch('/test', {
  5. method: "POST",
  6. body: JSON.stringify(data),
  7. headers: {"Content-Type": "application/json"},
  8. credentials: "same-origin"
  9. })
  10. .then(response => console.log(response.json))
  11. })
  12. </script>

每当我点击按钮来POST数据时,我在终端中看到以下内容:

POST
text/plain;charset=UTF-8
False

因此,我认为导致所有这些问题的原因是HTTP请求的Content-Type标头没有正确设置。

如果您有任何关于如何修复这个问题的想法,将不胜感激。

英文:

I was trying to send some JSON data to the sever following some online articles and the official flask documentation, but I keep getting a 400 error. What I've tried hasn't worked so far.

I have read that if flask doesn't get properly formated JSON data it pushes this error and also that the read of the request must specify Content-Type header as application/json or else the same happens.

I copied some of my code off the official Documentation and this is what i have so far:

a view function inside my flask application:

  1. @main.route(&#39;/test&#39;, methods=[&#39;GET&#39;,&#39;POST&#39;])
  2. def test():
  3. if request.method == &#39;POST&#39;:
  4. print(request.method)
  5. print(request.headers.get(&#39;Content-Type&#39;))
  6. print(request.is_json)
  7. #this gets me the 400 when run
  8. #print(request.json)
  9. return render_template(&#39;test.html&#39;)

the following scrip tag inside test.html:

  1. &lt;script&gt;
  2. let data = {&quot;data&quot;: &quot;Hello World!&quot;}
  3. document.querySelector(&#39;#main&#39;).addEventListener(&#39;click&#39;, function () {
  4. fetch(&#39;/test&#39;, {
  5. method: &quot;POST&quot;,
  6. body: JSON.stringify(data),
  7. headers: {&quot;Content-Type&quot;: &quot;application/json&quot;},
  8. credentials: &quot;same-origin&quot;
  9. })
  10. .then(response =&gt; console.log(response.json))
  11. })
  12. &lt;/script&gt;

Every time I hit the button to POST the data I get the following showing in my terminal

POST
text/plain;charset=UTF-8
False

So I assume what is causing all of this is that the Content-Type header of the HTTP request is not setting properly.

Any ideas on how I could fix this would be apreciated

答案1

得分: 1

需要指定您要定位的完整端点。

  1. from flask import Flask, request
  2. # 创建Flask应用
  3. app = Flask(__name__)
  4. # POST端点
  5. @app.route('/post', methods=['POST'])
  6. def endpoint():
  7. data = request.get_json()
  8. return data
  9. # 运行应用
  10. if __name__ == '__main__':
  11. app.run(debug=True)
  1. const endpoint = "http://127.0.0.1:5000/post";
  2. // 发送POST请求到端点
  3. const response = fetch(endpoint, {
  4. method: "POST",
  5. headers: {
  6. "Content-Type": "application/json"
  7. },
  8. body: JSON.stringify({
  9. name: "John Doe",
  10. })
  11. });
  12. response.then(data => {
  13. data.text().then(text => {
  14. console.log(text);
  15. })
  16. })
英文:

You need to specify the full endpoint of what you are targeting.

  1. from flask import Flask, request
  2. # create the flask app
  3. app = Flask(__name__)
  4. # post endpoint
  5. @app.route(&#39;/post&#39;, methods=[&#39;POST&#39;])
  6. def endpoint():
  7. data = request.get_json()
  8. return data
  9. # run the app
  10. if __name__ == &#39;__main__&#39;:
  11. app.run(debug=True)
  1. const endpoint = &quot;http://127.0.0.1:5000/post&quot;;
  2. // post request to endpoint
  3. const response = fetch(endpoint, {
  4. method: &quot;POST&quot;,
  5. headers: {
  6. &quot;Content-Type&quot;: &quot;application/json&quot;
  7. },
  8. body: JSON.stringify({
  9. name: &quot;John Doe&quot;,
  10. })
  11. });
  12. response.then(data =&gt; {
  13. data.text().then(text =&gt; {
  14. console.log(text);
  15. })
  16. })

答案2

得分: 0

根据您的代码和收到的错误消息,问题可能与请求头部设置不正确有关。

您在JavaScript代码中设置了Content-Type标头为"application/json",这是正确的。但是,您的Flask视图函数未正确检查Content-Type标头。您可以像这样检查:

  1. if request.is_json:
  2. data = request.get_json()
  3. print(data)
  4. else:
  5. print("请求不是JSON")

这会使用请求对象的is_json属性来检查请求是否为JSON格式。如果是,那么您可以使用get_json()方法提取数据。如果不是,您可以打印一条消息或返回一个错误。

此外,您可能还想添加一个try-except块来捕获解析JSON数据时可能发生的任何错误:

  1. if request.is_json:
  2. try:
  3. data = request.get_json()
  4. print(data)
  5. except Exception as e:
  6. print("解析JSON数据时出错:", e)
  7. return "请求无效", 400
  8. else:
  9. print("请求不是JSON")
  10. return "请求无效", 400

这将捕获解析JSON数据时的任何异常,并返回带有400状态代码的"请求无效"错误。

希望这有所帮助!

英文:

Based on your code and the error message you are receiving, the issue might be related to the request header not being set correctly.

You are setting the Content-Type header in your JavaScript code to "application/json", which is correct. However, your Flask view function does not check the Content-Type header correctly. You can check it like this:

  1. if request.is_json:
  2. data = request.get_json()
  3. print(data)
  4. else:
  5. print(&quot;Request is not JSON&quot;)

This checks whether the request is in JSON format using the is_json property of the request object. If it is, then you can use the get_json() method to extract the data. If it's not, you can print a message or return an error.

Additionally, you might want to add a try-except block to catch any errors that might occur when parsing the JSON data:

  1. if request.is_json:
  2. try:
  3. data = request.get_json()
  4. print(data)
  5. except Exception as e:
  6. print(&quot;Error parsing JSON data:&quot;, e)
  7. return &quot;Bad Request&quot;, 400
  8. else:
  9. print(&quot;Request is not JSON&quot;)
  10. return &quot;Bad Request&quot;, 400

This will catch any exceptions when parsing the JSON data and return a "Bad Request" error with a 400 status code.

I hope this helps!

huangapple
  • 本文由 发表于 2023年2月18日 04:30:46
  • 转载请务必保留本文链接:https://go.coder-hub.com/75489009.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定