Python HTTP简单服务器持久连接

时间:2019-04-19 15:49:41

标签: python http persistent

我正在尝试创建一个简单的HTTP服务器,该服务器将接收POST消息并提供简单的响应。我使用标准的HTTPServer和python。客户端使用应该使用持久连接的session()连接,但是在每次POST之后,我在调试中看到以下消息,表明连接已断开。

INFO:urllib3.connectionpool:重置断开的连接:

DEBUG:urllib3.connectionpool:“ GET / HTTP / 1.1” 200无

当我在Apache上尝试该客户端时,该客户端可以正常工作,因此我认为问题出在我的简单服务器配置中。如何配置简单的http服务器以与持久连接一起使用?

简单服务器Python代码:

from http.server import HTTPServer, BaseHTTPRequestHandler
from io import BytesIO
import time
import datetime
import logging


class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):

    def _set_response(self):
        self.send_response(200)
        self.send_header('Content-type', 'text/html')
        self.send_header("Connection", "keep-alive")
        self.send_header("keep-alive", "timeout=5, max=30")
        self.end_headers()

    def do_GET(self):
        self.send_response(200)
        self.end_headers()
        self.wfile.write(b'Hello, world!')

    def do_POST(self):
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)

        curr_time = datetime.datetime.now()
        data = ('{"msgid":"0x0002", "timestamp": "'+ str(curr_time) +'", "message":"Test http response from Raspberry Pi HTTP server"}').encode()

        self.send_response(200)
        self.end_headers()
        response = BytesIO()
        #response.write(b'This is POST request. ')
        #response.write(b'Received: ')
        response.write(data)
        self.wfile.write(response.getvalue())

print("Simple HTTP Server running...")
logging.basicConfig(level=logging.DEBUG)
httpd = HTTPServer(('', 8000), SimpleHTTPRequestHandler)
httpd.serve_forever()

客户端Python代码:

#!/usr/bin/env python

# Using same TCP connection for all HTTP requests

import os
import json
import time
import datetime
import logging
import requests
from requests.auth import HTTPBasicAuth

logging.basicConfig(level=logging.DEBUG)
start_time = time.time()

def get_data(limit):
    session = requests.Session()
    url = "http://localhost:8000"

    for i in range(10):
        curr_time = datetime.datetime.now()
        data = '{"msgid":"0x0001", "timestamp": "'+ str(curr_time) +'", "message":"Test http message from Raspberry Pi"}'

        print("Sending Data: " + data)

        response = session.post(url.format(limit), data)
        #response_dict = json.loads(response.text)
        print("Received Data: " + response.text)

if __name__ == "__main__":
  limit = 1
  get_data(limit)
  print("--- %s seconds ---" % (time.time() - start_time))

1 个答案:

答案 0 :(得分:0)

您实际上并没有在POST处理程序中设置Connection标头。为了使持久连接正常工作,您还需要在响应中设置Content-Length标头,以便客户端在重用连接之前知道要读取HTTP正文的多少字节。

尝试使用根据您的代码改编的POST处理程序:

   def do_POST(self):
        content_length = int(self.headers['Content-Length'])
        body = self.rfile.read(content_length)

        # Process the request here and generate the entire response
        response_data = b'{"stuff": 1234}'

        # Send the response
        self.send_response(200)
        self.send_header("Connection", "keep-alive")
        self.send_header("Content-Length", str(len(response_data)))
        self.end_headers()

        # Write _exactly_ the number of bytes specified by the
        # 'Content-Length' header
        self.wfile.write(response_data)