python怎样获得post原始数据(pickle.dumps产生的)?

问题描述

pickle.dumps返回的bytes数据,我想提交给服务器,但服务器接收到的是str(有部分会乱码)
我不知道bytes转换成str是在提交前发生的,还是在提交后发生的
是提交者requests的问题,还是接收者flask.request的问题,还是无可避免的问题
求解决办法(我想获得原始bytes数据)

问题出现的环境背景及自己尝试过哪些方法

先转为str再转回bytes是行不通的,因为pickle.dumps({})返回b'x80x03}qx00.'
而b'x80'无法decode,会报以下错误
UnicodeDecodeError: 'utf-8' codec can't decode byte 0x80 in position 0: invalid start byte

相关代码

// 请把代码文本粘贴到下方(请勿用图片代替代码)
in: b = pickle.dumps({})
in: b
out: b'x80x03}qx00.'
in: b.decode(encoding='UTF-8')
out: Traceback (most recent call last):
File "<stdin>", line 1, in <module>
UnicodeDecodeError: 'utf-8' codec can't decode byte 0x80 in position 0: invalid start byte

in: b
out: b'x80x03}qx00.'
in: b.decode(encoding='utf-16').encode(encoding='utf-16')
out: b'xffxfex80x03}qx00.'

综上,utf8无法解码,utf16的解码不可逆

你期待的结果是什么?实际看到的错误信息又是什么?

期待以下任一结果
1.从发送端解决
2.从接收端解决
3.一种对此可逆的编码

阅读 3.2k
1 个回答

如果你post的是表单
我想你说的乱码是这样吧

>>> from urllib.parse import quote, unquote
>>> from pickle import dumps
>>> b = dumps({})
>>> unquote(quote(b))
'�\x03}q\x00.'
>>>

因为表单数据请求时需要 urlencode (quote)编码,服务器解析时需要 urldecode (unquote)

原因在于 x80 可以被quote,但unquote时需要转换为str,默认编码是 'utf-8', 最后一句相当于

unquote(quote(b), encoding='utf-8', errors='replace')

errors='replace' 开启了编码容错,会把 x80 这样utf-8 无法编码的字符用特殊utf-8字符替代,这样也损失了数据准确性。

如果这样调用

>>> unquote(quote(b), errors='strict')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "d:\ProgramData\Anaconda3\lib\urllib\parse.py", line 621, in unquote
    append(unquote_to_bytes(bits[i]).decode(encoding, errors))
UnicodeDecodeError: 'utf-8' codec can't decode byte 0x80 in position 0: invalid start byte

就会抛异常

flask 并没有使用 urllib库,但是关于表单的urlencode实现差不多一致

所以如果你的请求头部 Content-Type 是 application/x-www-form-urlencoded; charset=UTF-8
就不要在表单里post二进制bytes数据

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题