socketserver模塊使用方法
一、socketserver模塊介紹
Python提供了兩個基本的socket模塊。一個是socket,它提供了標準的BSD Socket API; 另一個是socketserver,它提供了服務器中心類,可以簡化網絡服務器的開發
socketserver
socketserver內部使用IO多路復用以及“多線程”和“多進程”,從而實現並發處理多個客戶端請求的socket服務端。 即,每個客服端請求連接到服務器時,socket服務端都會在服務器上創建一個“線程”或“進程”專門負責處理當前客戶端的所有請求。
二、socketserver中的ThreadingTCPServer類
ThreadingTCPServer實現的socket服務器內部會為每個client創建一個“線程”,該線程用來和客戶端就行交互 ThreadingTCPServer源碼內容:
class ThreadingTCPServer(ThreadingMixIn, TCPServer): pass #可以看到ThreadTCPServer類本身並沒有方法,而是繼承了(ThreadingMinIn, TCPServer) 這兩個類。 而TCPServer則是繼承了BaseServer類。
三、ThreadingTCPServer的使用方法
1、創建一個繼承socketserver.BaseRequestHandler的類
2、類中必須重寫一個名為handler的方法
3、實例化一個服務器類,傳入服務器的地址和請求處理程序類
4、調用serve_forever()事件循環監聽
#!/usr/bin/env python3 import socketserver class Handler(socketserver.BaseRequestHandler): # 必須繼承BaseRequestHandler def handle(self): # 必須有handle方法 print(‘New connection:‘,self.client_address) while True: data = self.request.recv(1024) if not data:breakView Codeprint(‘Client data:‘,data.decode()) self.request.send(data) if __name__ == ‘__main__‘: server = socketserver.ThreadingTCPServer((‘127.0.0.1‘,8009),Handler) # 實例化對象,實現多線程的socket server.serve_forever() # 事件監聽,並調用handler方法
四、ThreadingTCPServer執行過程
1、啟動服務端程序
2、執行TCPServer.__init__方法,創建服務端socket對象並綁定IP和端口(根據類的繼承關系,即查找順序找到TCPServer.__init__())
3、執行BaseServer.__init__方法,將自定義的繼承自socketserver.BaseRequestHandler的類MyRequestHandler賦值給self.RequestHandlerClass class TCPServer(BaseServer): #(繼承了BaseServeer類)
class TCPServer(BaseServer): #(繼承了BaseServeer類) def __init__(self, server_address, RequestHandlerClass, bind_and_activate=True): """Constructor. May be extended, do not override.""" BaseServer.__init__(self, server_address, RequestHandlerClass) #(重寫了BaseServer的__init__方法) self.socket = socket.socket(self.address_family, self.socket_type) if bind_and_activate: try: self.server_bind() self.server_activate() except: self.server_close() raise class BaseServer: def __init__(self, server_address, RequestHandlerClass): #(接收了兩個傳進來的參數) """Constructor. May be extended, do not override.""" self.server_address = server_address self.RequestHandlerClass = RequestHandlerClass #(賦值給了self.RequestHandlerClass) self.__is_shut_down = threading.Event() self.__shutdown_request = FalseView Code
4、通過實例化的對象,執行serve_forever方法,該方法首先查找到BaseServer下的方法,通過調用selector模塊,註冊事件監聽對象,並執行_handle_request_noblock方法 找到此方法,並調用該方法下的process_request方法,在此調用到finish_request方法,通過finish_request方法,執行了RequestHandlerClass方法,執行此方法就相當於調用 了我們重寫的Handler類。
class BaseServer: def serve_forever(self, poll_interval=0.5): try: with _ServerSelector() as selector: selector.register(self, selectors.EVENT_READ) while not self.__shutdown_request: ready = selector.select(poll_interval) if ready: self._handle_request_noblock() self.service_actions() def _handle_request_noblock(self): try: request, client_address = self.get_request() except OSError: return if self.verify_request(request, client_address): try: self.process_request(request, client_address) except Exception: self.handle_error(request, client_address) self.shutdown_request(request) except: self.shutdown_request(request) raise else: self.shutdown_request(request) def process_request(self, request, client_address): self.finish_request(request, client_address) self.shutdown_request(request) def finish_request(self, request, client_address): self.RequestHandlerClass(request, client_address, self)View Code
5、通過Handler類實例化對象,調用繼承的BaseRequestHandler類中的__init__方法,並執行了handler方法。 從而運行了我們重寫Handler類中的handler方法。
class BaseRequestHandler: def __init__(self, request, client_address, server): self.request = request self.client_address = client_address self.server = server self.setup() try: self.handle() #調用handler() finally: self.finish()View Code
五、調用流程圖
socketserver模塊使用方法