我有類似蟒蛇聊天室編寫打算做以下事情的應用程序:如何停止的WebSocket客戶端無需停止反應堆
- 對用戶輸入的WebSocket服務器地址的提示。
- 然後創建一個連接到服務器併發送/接收消息的websocket客戶端。禁用創建websocket客戶端的功能。
- 在收到服務器的「關閉」(不是關閉幀)後,客戶端應該斷開連接並重新啓用應用程序以創建客戶端。返回1.
- 如果用戶退出應用程序,它將退出websocket客戶端(如果有一個正在運行)。
我的方法是使用主線程來處理用戶輸入。當用戶輸入時,使用AutoBahn的扭曲模塊爲WebSocketClient創建一個線程,並將一個隊列傳遞給它。檢查反應堆是否在運行,如果不是,則啓動反應堆。 覆蓋消息方法以在「關閉」時將關閉標誌放入隊列中。主線程將忙於檢查隊列,直到收到標誌並返回開始。代碼如下所示。
主線程。
def main_thread():
while True:
text = raw_input("Input server url or exit")
if text == "exit":
if myreactor:
myreactor.stop()
break
msgq = Queue.Queue()
threading.Thread(target=wsthread, args=(text, msgq)).start()
is_close = False
while True:
if msgq.empty() is False:
msg = msgq.get()
if msg == "close":
is_close = True
else:
print msg
if is_close:
break
print 'Websocket client closed!'
工廠和協議。
class MyProtocol(WebSocketClientProtocol):
def onMessage(self, payload, isBinary):
msg = payload.decode('utf-8')
self.Factory.q.put(msg)
if msg == 'close':
self.dropConnection(abort=True)
class WebSocketClientFactoryWithQ(WebSocketClientFactory):
def __init__(self, *args, **kwargs):
self.queue = kwargs.pop('queue', None)
WebSocketClientFactory.__init__(self, *args, **kwargs)
客戶端線程。
def wsthread(url, q):
factory = WebSocketClientFactoryWithQ(url=url, queue=q)
factory.protocol = MyProtocol
connectWS(Factory)
if myreactor is None:
myreactor = reactor
reactor.run()
print 'Done'
現在我遇到了問題。看來我的客戶端線程永遠不會停止。即使我收到「close」,它似乎仍在運行,每次我嘗試重新創建一個新客戶端時,它都會創建一個新線程。我知道第一個線程不會停止,因爲reactor.run()
將永遠運行,但從第二個線程開始,它應該是非阻塞的,因爲我不再啓動它。我該如何改變它?
編輯:
我結束了
- 斷開連接後添加
stopFactory()
解決它。 - 使協議功能與
reactor.callFromThread()
。 - 在第一個線程中啓動反應器並將客戶端放入其他線程並使用
reactor.callInThread()
來創建它們。
服務器可以關閉客戶端套接字,是否要處理服務器上的所有客戶端錯誤? – dsgdfg
@dsgdfg事實是,我試圖複製一個現有的應用程序,但我沒有自己的客戶端或服務器,所以我沒有代碼。從我所知道的使用wireshark,我可以看到服務器發送消息「關閉」,客戶端回覆代碼爲1001的關閉幀並退出。我想要做同樣的事情,但我不知道如何關閉客戶端並讓線程返回,以便我可以做其他工作。 – vance46