1099 Stimmen

Wie POST JSON-Daten mit Python-Anfragen?

Ich brauche POST ein JSON von einem Client zu einem Server. Ich bin mit Python 2.7.1 und simplejson. Der Client verwendet Requests. Der Server ist CherryPy. Ich kann GET eine hart codierte JSON vom Server (Code nicht angezeigt), aber wenn ich versuche, POST eine JSON an den Server, erhalte ich "400 Bad Request".

Hier ist mein Client-Code:

data = {'sender':   'Alice',
    'receiver': 'Bob',
    'message':  'We did it!'}
data_json = simplejson.dumps(data)
payload = {'json_payload': data_json}
r = requests.post("http://localhost:8080", data=payload)

Hier ist der Server-Code.

class Root(object):

    def __init__(self, content):
        self.content = content
        print self.content  # this works

    exposed = True

    def GET(self):
        cherrypy.response.headers['Content-Type'] = 'application/json'
        return simplejson.dumps(self.content)

    def POST(self):
        self.content = simplejson.loads(cherrypy.request.body.read())

Irgendwelche Ideen?

1774voto

Zeyang Lin Punkte 16598

Ab der Requests-Version 2.4.2 können Sie die json= Parameter (das ein Wörterbuch benötigt) anstelle von data= (der eine Zeichenkette annimmt) im Aufruf:

>>> import requests
>>> r = requests.post('http://httpbin.org/post', json={"key": "value"})
>>> r.status_code
200
>>> r.json()
{'args': {},
 'data': '{"key": "value"}',
 'files': {},
 'form': {},
 'headers': {'Accept': '*/*',
             'Accept-Encoding': 'gzip, deflate',
             'Connection': 'close',
             'Content-Length': '16',
             'Content-Type': 'application/json',
             'Host': 'httpbin.org',
             'User-Agent': 'python-requests/2.4.3 CPython/3.4.0',
             'X-Request-Id': 'xx-xx-xx'},
 'json': {'key': 'value'},
 'origin': 'x.x.x.x',
 'url': 'http://httpbin.org/post'}

551voto

Charles R Punkte 17141

Es stellte sich heraus, dass ich die Kopfzeileninformationen übersehen hatte. Das Folgende funktioniert:

import requests

url = "http://localhost:8080"
data = {'sender': 'Alice', 'receiver': 'Bob', 'message': 'We did it!'}
headers = {'Content-type': 'application/json', 'Accept': 'text/plain'}
r = requests.post(url, data=json.dumps(data), headers=headers)

101voto

ZZY Punkte 3429

Aus den Anträgen 2.4.2 ( https://pypi.python.org/pypi/requests ), wird der Parameter "json" unterstützt. Die Angabe von "Content-Type" ist nicht erforderlich. Also die kürzere Version:

requests.post('http://httpbin.org/post', json={'test': 'cheers'})

81voto

xiaoming Punkte 919

Welcher Parameter zwischen data / json / files die Sie verwenden müssen, hängt von einem Anfragekopf namens Content-Type (Sie können dies über die Entwicklertools Ihres Browsers überprüfen).

Wenn die Content-Type es application/x-www-form-urlencoded verwenden data= :

requests.post(url, data=json_obj)

Wenn die Content-Type es application/json verwenden, können Sie entweder einfach json= oder verwenden data= und setzen Sie die Content-Type selbst:

requests.post(url, json=json_obj)

requests.post(url, data=jsonstr, headers={"Content-Type":"application/json"})

Wenn die Content-Type es multipart/form-data wird zum Hochladen von Dateien verwendet, also verwenden Sie files= :

requests.post(url, files=xxxx)

50voto

ellen Punkte 537

Der bessere Weg ist

url = "http://xxx.xxxx.xx"
data = {
    "cardno": "6248889874650987",
    "systemIdentify": "s08",
    "sourceChannel": 12
}
resp = requests.post(url, json=data)

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X