在http.client或python-requests中获取http原始(未解析的)响应

时间:2019-04-22 13:59:51

标签: python http python-requests

我正在使用Python发出HTTP请求。我需要原始的HTTP响应如下所示:

flutter update

在python请求中,我尝试了HTTP/1.1 200 OK Date: Mon, 19 Jul 2004 16:18:20 GMT Server: Apache Last-Modified: Sat, 10 Jul 2004 17:29:19 GMT ETag: "1d0325-2470-40f0276f" Accept-Ranges: bytes Content-Length: 9328 Connection: close Content-Type: text/html <HTML> <HEAD> ... the rest of the home page... ,但这不是原始HTTP响应,它只是原始正文。

不使用response.raw可以实现这一目标吗?

P.S。我不想使用已解析的部分重建原始响应。

1 个答案:

答案 0 :(得分:0)

requests没有拥有状态行和原始格式的标题。您永远不需要原始格式的文件,可以从您拥有的数据中轻松地重建符合RFC的响应。 requests使用urllib3 library作为基础,而该库又使用Python标准库http.client module。该模块不会向您提供原始数据

相反,状态行和标头直接解析为http.client.HTTPResponse._read_status()http.client.parse_headers()中的组成部分(后者委托给email.parser.Parser().parsestr() method来将标头解析为{{3 }})。仅使用这些解析操作的结果。

您可以尝试包装urllib3连接对象(通过在http.client.HTTPMessage() instance上实现的get_connection() hook)。连接对象具有创建套接字对象的requests transport adapter,如果您将它们包装在类似文件的对象中,然后查看.readline()调用数据,则可以在其中捕获并存储原始数据。

但是,如果您要调试损坏的HTTP服务器,在这里我不会尝试弯曲requests及其堆栈。只需在命令行上使用curl --include --raw <url>(也许添加了--verbose)即可。

另一种选择是直接使用http.client库,建立连接,使用.connect() method with supporting methods发送传出标头,然后使用getresponse(),而只是直接从conn.sock读取。