在flask python

时间:2016-05-30 10:31:00

标签: python json flask webserver flask-restful

我已经在python中编写了一个简单的REST-ful Web服务器,其中flask执行了此tutorial中的步骤;但我在调用POST请求时遇到问题。代码是:

@app.route('/todo/api/v1.0/tasks', methods=['POST'])
def create_task():
    if not request.json or not 'title' in request.json:
        abort(400)
    task = {
        'id': tasks[-1]['id'] + 1,
        'title': request.json['title'],
        'description': request.json.get('description', ""),
        'done': False
    }
    tasks.append(task)
    return jsonify({'task': task}), 201

我使用POST发送curl请求作为上述页面中的示例:

curl -i -H "Content-Type: application/json" -X POST -d '{"title":"Read a book"}' http://127.0.0.1:5000/todo/api/v1.0/tasks

但我在回复时收到此错误:

HTTP/1.0 400 BAD REQUEST
Content-Type: text/html
Content-Length: 187
Server: Werkzeug/0.11.10 Python/2.7.9
Date: Mon, 30 May 2016 09:05:52 GMT

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<title>400 Bad Request</title>
<h1>Bad Request</h1>
<p>Failed to decode JSON object: Expecting value: line 1 column 1 (char 0)</p>

我已尝试调试,并且我在get_json方法中发现,已传递的参数已转换为'\\'{title:Read a book}\\'' datarequest_charset为{ {1}};但我不知道解决方案。有什么帮助吗?

编辑1:

我已经尝试了@ domoarrigato的回答并实施了None方法,如下所示:

create_task

但这次我通过@app.route('/todo/api/v1.0/tasks', methods=['POST']) def create_task(): try: blob = request.get_json(force=True) except: abort(400) if not 'title' in blob: abort(400) task = { 'id': tasks[-1]['id'] + 1, 'title': blob['title'], 'description': blob.get('description', ""), 'done': False } tasks.append(task) return jsonify({'task': task}), 201 致电POST时收到以下错误:

curl

编辑2:

为了澄清,我应该提到我正在使用64位版本的Microsoft Windows 7和Python 2.7以及最新版本的Flask。

7 个答案:

答案 0 :(得分:13)

这适用于Windows 7 64:

curl -i -H "Content-Type: application/json" -X POST -d "{\"title\":\"Read a book\"}" http://localhost:5000/todo/api/v1.0/tasks

反斜线和双引号。

答案 1 :(得分:3)

如果您使用的是Windows,请求中的json字符串应如下所示:

"{\"title\":\"Read a boo\"}"

我遇到了同样的问题并且有所帮助。

答案 2 :(得分:2)

我设法使它使用Anaconda cmd窗口,python3,并在整个表达式中使用反斜杠和双引号! 作品:

curl "localhost:5000/txion" -H "Content-Type: application/json" -d "{\"from\": \"akjflw\" ,\"to\" : \"fjlakdj\", \"amount\": 4}"

不起作用:

curl "localhost:5000/txion" -H "Content-Type: application/json" -d '{\"from\": \"akjflw\" ,\"`to\" : \"fjlakdj\", \"amount\": 4}'

答案 3 :(得分:1)

不要使用request.json属性,请尝试使用request.get_json(force=True)我会重写它:

@app.route('/todo/api/v1.0/tasks', methods=['POST'])
def create_task():
    try:
        blob = request.get_json(force=True)
    except:
        abort(400)
    if not 'title' in blob:
        abort(400)
    task = {
        'id': tasks[-1]['id'] + 1,
        'title': blob['title'],
        'description': blob.get('description', ""),
        'done': False
    }
    tasks.append(task)
    return jsonify({'task': task})

答案 4 :(得分:0)

只需在JSON字符串中使用“而不是”,并在JSON字符串中的任何“之前”放置\。

答案 5 :(得分:0)

如果您使用Powershell来使用CURL,则需要专门使用$(x)(而不是x)添加“哑解析”标记curl.exe

然后您要做的就是将它双引号,并在JSON中转义双引号。单引号似乎不起作用。

curl

答案 6 :(得分:-1)

from flask import Flask, request, abort, jsonify

app = Flask(__name__)
tasks = [{'id': 0}]

@app.route('/todo/api/v1.0/tasks', methods=['POST'])
def create_task():
    if not request.json or 'title' not in request.json:
        abort(400)
    task = {
        'id': tasks[-1]['id'] + 1,
        'title': request.json['title'],
        'description': request.json.get('description', ""),
        'done': False
    }
    tasks.append(task)
    response = {"task": task}
    return jsonify(response), 201

if __name__ == '__main__':
    app.run(host='0.0.0.0', port=5000, debug=True)

卷曲:

curl -i -H "Content-Type: application/json" -X POST -d '{"title":"Read a book"}' http://127.0.0.1:5000/todo/api/v1.0/tasks

OP:

{
  "task": {
    "description": "", 
    "done": false, 
    "id": 1, 
    "title": "Read a book"
  }
}