Pyqt; QTcpSocket всегда в connectionState после перезапуска сервера;

У меня есть подкласс QTcpSocket. И проблема в том, что когда я подключаюсь к серверу – все нормально, но после подключения сокета я перезапускаю сервер (python socketServer, просто закройте и запустите скрипт снова). Отключение разъема и попытка повторного подключения во время работы сервера, но когда я снова запустил сервер – ничего не произошло, socket.state () всегда в ConnectionState .. что не так?

Вот пример кода:

# -*- coding: utf-8 -*- from PyQt4.QtCore import QVariant, QTimer, pyqtSignal, QCoreApplication import sys from PyQt4.QtNetwork import QTcpSocket from re import match import json MAX_WAIT_LEN = 8 class UpQSocket(QTcpSocket): data_ready = pyqtSignal(unicode) def __init__(self): QTcpSocket.__init__(self) self.wait_len = '' self.temp = '' self.setSocketOption(QTcpSocket.KeepAliveOption, QVariant(1)) self.readyRead.connect(self.on_ready_read) self.connected.connect(self.on_connected) self.disconnected.connect(self.on_disconnect) self.error.connect(self.on_error) self.data_ready.connect(self.print_command) def connectToHost(self, host, port): print 'connectToHost' self.temp = '' self.wait_len = '' QTcpSocket.abort(self) QTcpSocket.connectToHost(self, host, port) def close(self): print 'close!' self.disconnectFromHost() def send(self, data): self.writeData('%s|%s' % (len(data), data)) def on_ready_read(self): if self.bytesAvailable(): data = str(self.readAll()) while data: if not self.wait_len and '|' in data:#new data and new message self.wait_len , data = data.split('|',1) if match('[0-9]+', self.wait_len) and (len(self.wait_len) <= MAX_WAIT_LEN) and data.startswith('{'):#okay, this is normal length self.wait_len = int(self.wait_len) self.temp = data[:self.wait_len] data = data[self.wait_len:] else:#oh, it was crap self.wait_len , self.temp = '','' return elif self.wait_len:#okay, not new message, appending tl= int(self.wait_len)-len(self.temp) self.temp+=data[:tl] data=data[tl:] elif not self.wait_len and not '|' in data:#crap return if self.wait_len and self.wait_len == len(self.temp):#okay, full message self.data_ready.emit(self.temp) self.wait_len , self.temp = '','' if not data: return def print_command(self,data): print 'data!' def get_sstate(self): print self.state() def on_error(self): print 'error', self.errorString() self.close() self.connectToHost('dev.ulab.ru', 10000) def on_disconnect(self): print 'disconnected!' def on_connected(self): print 'connected!' self.send(json.dumps( {'command' : "operator_insite", 'password' : "376c43878878ac04e05946ec1dd7a55f", 'login' : "nsandr", 'version':unicode("1.2.9")})) if __name__ == "__main__": app = QCoreApplication(sys.argv) main_socket = UpQSocket() state_timer = QTimer() state_timer.setInterval(1000) state_timer.timeout.connect(main_socket.get_sstate) state_timer.start() main_socket.connectToHost('dev.ulab.ru', 10000) sys.exit(app.exec_()) 

Вот вывод:

  connectToHost 1 1 connected! data! data! 3 3 3 3 3 error The remote host closed the connection close! disconnected! connectToHost 2 2 

    One Solution collect form web for “Pyqt; QTcpSocket всегда в connectionState после перезапуска сервера;”

    Временное решение:

     import functools def on_error(self): print 'error', self.errorString() QTimer.singleShot(2000, functools.partial(self.connectToHost, 'localhost', 9999)) # 2000 - your prefered reconnect timeout in ms 

    Обновить

    В комментариях для Qt bugreport QTBUG-18082 есть более правильное решение. Вот реализация Python:

     @QtCore.pyqtSlot() def do_reconnect(self): print 'Trying to reconnect' self.connectToHost('localhost', 9999) def on_error(self): print 'error', self.errorString() QtCore.QMetaObject.invokeMethod(self, 'do_reconnect', QtCore.Qt.QueuedConnection) 

    или просто:

     QTimer.singleShot(0, self.do_reconnect) # or any callable, slot is unnecessary 

    который в любом случае вызовет QtCore.QMetaObject.invokeMethod с QueuedConnection QtCore.QMetaObject.invokeMethod QueuedConnection ( source )

    Python - лучший язык программирования в мире.