django 异常错误:阅读请求的数据流后无法访问正文

iyr7buue  于 2022-11-19  发布在  Go
关注(0)|答案(7)|浏览(162)

因为Django 1.5的原始发布数据可以通过request.body访问。
在我的应用程序中,我有时会通过一个表单接收数据,有时会接收原始数据(例如json)。有没有什么方法可以编写这样一个不会失败的函数?

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
pinkon5k

pinkon5k1#

使用request.data而不是request.body
request.data不再读取数据流。

zrfyljdw

zrfyljdw2#

如果(1)请求方法是POST,(2)在中间件中访问请求的POST字典,在process_requestprocess_view中,以及(3)在视图函数中访问request.body,则会在请求上触发错误You cannot access body after reading from request's data stream。即使错误的真实的原因是(2),也会在(3)上引发错误。
为了解决这个错误,您需要检查中间件在哪里访问request.POST,并修改它,使它不再访问request.POST
Django的文档说middleware should not access request.POST,这是忽略这个建议的一个后果。
还可以查看this Django ticket on the issue,其中包括以下注解:
命中请求的[M]iddleware。POST(通常)应视为Bug。这意味着视图将无法设置任何自定义上载处理程序,执行请求正文的自定义语法分析,或在接受文件上载之前强制执行权限检查。

qyuhtwio

qyuhtwio3#

除了Adam Easterling的回答之外,值得注意的是Django本身“违反了”使用中间件中的request.POST的提示:
可以将CsrfViewMiddleware类视为一个例外,因为它提供了csrf_exempt()和csrf_protect()装饰器,允许视图显式控制CSRF验证应该在什么时候进行。
这并不能消除违反IMO的行为

zy1mlcev

zy1mlcev4#

对于那些有兴趣知道,我面临这个问题:
阅读请求的数据流后无法访问正文
当我oauth2_provider.contrib.rest在“REST_FRAMEWORK”中添加“www.example.com_framework.OAuth2Authentication”时,就像在www.example.com中一样settings.py:

REST_FRAMEWORK = {
   ...
    'DEFAULT_AUTHENTICATION_CLASSES': (
      ...
       'oauth2_provider.contrib.rest_framework.OAuth2Authentication',
      ...
    ),

当然,禁用这将工作,但不是一个变通办法,我会感到自豪。

jmp7cifd

jmp7cifd5#

在我的视图函数前放置@csrf_exempt后,我能够读取我的请求。POST。因为CSRF中间件访问POST数据。

ajsxfq5m

ajsxfq5m6#

我发现了一个窍门,用于我的中间件,

request._read_started = False

在这样做之后,再次准备身体,它就工作了。

ffdz8vbo

ffdz8vbo7#

对于那些没有准备好主体或POST的人,当我在process_view中间件中使用这行代码时,我也遇到了同样的错误:

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

通过设置请求解决。函数顶部的event = None,这样我就可以用途:

event = request.event

相关问题