webentwicklung-frage-antwort-db.com.de

Ausnahme: Nach dem Lesen aus dem Datenstrom der Anforderung können Sie nicht auf den Textkörper zugreifen

Seit Django 1.5 sind Rohdaten über request.body verfügbar.

In meiner Anwendung bekomme ich manchmal Daten über ein Formular und manchmal Rohdaten (z. B. Json). Gibt es eine Möglichkeit, eine solche Funktion zu schreiben, die nicht fehlschlägt?

def get_post_var(request, name):
    result = request.POST.get(name)
    if result:
        return result

    post_body = dict(urlparse.parse_qsl(request.body))
    result = post_body.get(name)
    if result:
        return result

    return None
18
kev

Der Fehler You cannot access body after reading from request's data stream wird bei einer Anforderung ausgelöst, wenn (1) diese Anforderungsmethode POST ist, (2) auf das Verzeichnis POST der Anforderung in der Middleware in process_request oder process_view und (3) innerhalb der View-Funktion zugegriffen wird wird auf request.body zugegriffen. Auf (3) wird der Fehler ausgelöst, obwohl die eigentliche Fehlerursache (2) ist.

Um den Fehler zu beheben, müssen Sie Ihre Middleware untersuchen, wo sie auf request.POST zugreift, und sie so ändern, dass sie nicht mehr auf request.POST zugreift.

Die Django-Dokumente sagen, dass Middleware nicht auf request.POST zugreifen sollte, und dies ist eine Folge des Ignorierens dieser Empfehlung.

Check-out dieses Django-Ticket zur Ausgabe , das den Hinweis enthält:

[M] iddleware, die request.POST trifft, sollte (normalerweise) als - Fehler betrachtet werden. Dies bedeutet, dass die Ansicht keine benutzerdefinierten Upload-Handler Festlegen, eine benutzerdefinierte Analyse des Anforderungstextes durchführen oder Berechtigungsprüfungen erzwingen kann, bevor Datei-Uploads akzeptiert werden.

22
Adam Easterling

Zu Adam Easterlings Antwort kommt noch hinzu, dass Django selbst ' verletzt ' den Hinweis von nicht mit request.POST in der Middleware verwendet:

Die CsrfViewMiddleware-Klasse kann als Ausnahme betrachtet werden, da Die Dekoratoren csrf_exempt () und csrf_protect () bereitstellt, mit denen -Sichten explizit steuern können, zu welchem ​​Zeitpunkt die CSRF-Überprüfung Erfolgen soll .

Die sanktioniert die Verletzung der IMO nicht

7
Romeno

Verwenden request.data anstatt request.body.

request.data liest den Datenstrom nicht erneut.

3
Arnab Biswas

Ich konnte meine request.POST lesen, nachdem ich @csrf_exempt vor meine View-Funktion gestellt hatte. Weil die CSRF-Middleware auf POST -Daten zugreift.

0
Sia

Für diejenigen mit demselben Fehler, die den Body oder den POST nicht vorbereiten, trat derselbe Fehler auf, als ich diese Codezeile in einer process_view-Middleware verwendete:

   event = request.event if 'event' in request else None

Gelöst durch Einstellungen request.event = Keine am oberen Rand der Funktion, so dass ich dann verwenden könnte:

    event = request.event
0
PhoebeB