我正在Python中編寫客戶端/服務器應用程序,我發現有必要爲客戶端的每個請求獲取到服務器的新連接。我的服務器只是從TCPServer繼承而來,我從BaseRequestHandler繼承來完成我的處理。我沒有在處理程序中的任何地方調用self.request.close(),但不知何故服務器似乎掛在我的客戶端上。這是怎麼回事?Python的SocketServer中的TCPServer + BaseRequestHandler在每次調用handle()後關閉套接字嗎?
9
A
回答
7
好吧,我閱讀代碼(我的Mac上,SocketServer.py是/System/Library/Frameworks/Python.framework/Versions/2.5/ LIB /的python2.5 /)。
的確,TCPServer正在關閉連接。在BaseServer.handle_request
中,調用process_request
,調用close_request
。在TCPServer類中,close_request
調用self.request.close()
,而self.request
只是用於處理請求的套接字。
所以我的問題的答案是「是」。
0
您確定客戶端沒有掛在服務器上?這有點太模糊,不能真正說出發生了什麼,但通常情況下,接受來自客戶端數據的服務器將退出讀取連接,不返回任何數據。
6
根據文檔,除非被提示,否則TCPServer和BaseRequestHandler都不會關閉套接字。 handle()
和finish()
的默認實現什麼也不做。
幾件事情可能會發生:
- 您關閉套接字本身或包裝它的請求,或致電
server_close
地方。 - 套接字超時可能已經命中,並且您已經實現了一個關閉套接字的超時處理程序。
- 客戶端可能實際上關閉了套接字。代碼真的有助於解決這個問題。
但是,我的測試證實了你的結果。一旦從服務器上的handle
返回,無論是通過telnet或Python的socket
模塊進行連接,您的連接顯示爲由遠程主機關閉。在內側把手循環處理套接字活動似乎工作:
def handle(self):
while 1:
try:
data = self.request.recv(1024)
print self.client_address, "sent", data
except:
pass
一個簡短的谷歌代碼搜索證實,這是處理請求的典型方式:1234。老實說,有很多其他網絡庫可用於Python,如果我面臨抽象SocketServer
提供和我的期望之間的斷開,我可能會看到。
代碼示例:
from SocketServer import BaseRequestHandler, TCPServer
class TestRequestHandler(BaseRequestHandler):
def handle(self):
data = self.request.recv(1024)
print self.client_address, "sent", data
self.request.send(data)
class TestServer(TCPServer):
def __init__(self, server_address, handler_class=TestRequestHandler):
TCPServer.__init__(self, server_address, handler_class)
if __name__ == "__main__":
import socket
address = ('localhost', 7734)
server = TestServer(address)
server.socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
5
- 的tcpserver非常接近 '句柄' 後,每次連接
,同時對關閉
def handle(self): while 1: try: data = self.request.recv(1024) print self.client_address, "sent", data except: pass
後續的代碼不能正常工作,這可能會更好:
def handle(self): while(1): try: self.data = self.request.recv(1024) if not self.data: print "%s close" % self.client_address[0] break print "%s wrote:" % self.client_address[0], self.data except: print "except" break
reuseaddr
不起作用,因爲綁定後太遲
server.socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
相關問題
- 1. Python SocketServer-繼承BaseRequestHandler的目的
- 2. ruby中的TCPServer套接字
- 3. 每次交易後我應該關閉一個套接字(TCPIP)嗎?
- 4. Ruby TCPServer套接字
- 5. 套接字關閉後關閉線程
- 6. 在關閉的unix套接字上關閉socket.accept()調用
- 7. Python socketserver或帶線程套接字
- 8. 我應該在Python中顯式關閉zeromq套接字嗎?
- 9. 每次查詢後關閉MySQL連接
- 10. 在調用close之前關閉套接字但不關閉
- 11. 在每次HTTP事務之後,什麼會導致套接字快速關閉?
- 12. 在fork()後關閉監聽套接字()
- 13. 檢查套接字後sock.shutdown(SHUT_WR)關閉?
- 14. 每次發佈後我應該關閉頻道/連接嗎?
- 15. 沒有關閉被調用,本地端可以關閉套接字嗎?
- 16. Python中的多個套接字/重用/關閉套接字? _socketobject錯誤
- 17. 關閉套接字?
- 18. FTP實現:每次關閉數據套接字
- 19. 關閉的SocketServer上SIG *
- 20. 如何在不關閉套接字的情況下多次調用套接字發送和接收?
- 21. perl的關閉套接字
- 22. 關閉套接字
- 23. 我需要關閉套接字嗎?
- 24. 是Xively web套接字關閉了嗎?
- 25. 關閉套接字後,套接字連接保持ESTABLISHED
- 26. Java套接字在關閉5分鐘之後仍然關閉
- 27. 自動關閉套接字python
- 28. Python TCP套接字不能關閉?
- 29. Python隨機關閉套接字似乎
- 30. java套接字SocketException套接字關閉
這是UNIX或Windows?你能發佈客戶端的代碼片段嗎? – Richie 2010-01-14 19:21:36
答案在代碼中是正確的...看看BaseHTTPServer.py和SocketServer.py – ChristopheD 2010-01-14 19:49:07
感謝您的指點。我很想知道答案,而不是在哪裏找到答案。 – 2010-01-14 23:10:45