我目前正在编写一个应用程序,它需要能够通过网络连接到自己的另一个实例。我使用python的套接字模块创建了一个tcpip套接字。我有一个服务器类,它等待客户端(使用客户端类)连接。当发生连接时,服务器然后为自己创建另一个客户端类实例,用于通信。这些由他们自己的"处理程序"管理,它具有发送和接收数据的方法。
我可以运行服务器的一个实例并与客户端连接就好了。我甚至可以从服务器(客户端)向接收客户端发送消息。但是当我尝试从客户端向服务器发送消息时,我的问题就出现了。虽然服务器确实接收到数据,但我用来让处理程序抓取数据的qt信号不会触发。我很困惑,因为服务器和客户端都使用相同的类进行通信,代码相同。我似乎无法弄清楚出了什么问题。
这是服务器类,它唯一的目的是接受连接。
class Server(threading.Thread):
def __init__(self, parent, network_type, port = 64355):
threading.Thread.__init__(self)
self.socket = socket.socket(
socket.AF_INET,
socket.SOCK_STREAM
)
if network_type == "LAN":
self.socket.bind(("localhost",port))
self.address = "localhost"
elif network_type == "INTERNET":
self.socket.bind((socket.gethostname(),port))
self.address = socket.gethostname()
else:
raise AttributeError("Invalid network type specified, use LAN or INTERNET.")
self.ct = False
self.port = port
self.parent = parent
def run(self):
while self.ct == False:
self.socket.listen(1)
(clientsocket, address) = self.socket.accept()
print(clientsocket)
self.ct = Client(self.parent,clientsocket)
self.parent.have_connected()
这是客户端类,它使用线程'监听器'监视套接字的数据。
class Client(object):
def __init__(self, parent, sock = False):
if sock:
self.socket = sock
else:
self.socket = socket.socket(
socket.AF_INET,
socket.SOCK_STREAM
)
self.listener = False
self.parent = parent
def connect(self, address, port = 64355):
try:
self.parent.append_text1("looking for host at {}:{}".format(address,port))
print(self.socket)
self.socket.connect((address,port))
self.parent.have_connected()
except Exception as e:
print(e)
return
def send(self,data):
totalsent = 0
while totalsent < len(data):
sent = self.socket.send(data[totalsent:])
if sent == 0:
raise RuntimeError("socket connection broken")
totalsent = totalsent + sent
def listen(self):
self.listener = Listener(self.parent,self.socket)
self.listener.start()
这是线程监听器,如上所述。
class Listener(threading.Thread):
def __init__(self, parent,sock):
threading.Thread.__init__(self)
self.parent = parent
self.cache = ""
self.socket = sock
print(self.parent)
self.obj = QtGui.QWidget()
QtCore.QObject.connect(self.obj, QtCore.SIGNAL("data_recv()"), nethandler.data_received)
def run(self):
while True:
data = self.socket.recv(4096).decode()
self.cache += data
self.obj.emit(QtCore.SIGNAL("data_recv()"))
最后,当侦听器接收到新数据时,应该触发其data_received()方法的处理程序。
class NetHandler(object):
def __init__(self):
self.connected = False
self.is_server = False
def set_as_host(self,network_type,port):
self.server = Server(self,network_type,port)
self.server.start()
self.is_server = True
def set_as_client(self):
self.client = Client(self)
def have_connected(self):
self.connected = True
if self.is_server:
self.client = self.server.ct
self.server.close()
self.client.listen()
def data_received(self):
if self.client.listener == False:
return
data = self.client.listener.cache
self.client.listener.cache = ""
if data.startswith("::CHAT::"):
print("Chat message: "+data[8:]
def send_chat(self, text):
if self.connected:
self.client.send(("::CHAT::"+text).encode())