我正在使用多线程TCP服务器。 每个套接字都作为每个客户端的单独线程创建。我想通过socket的send()方法向所有客户端发送数据。我面临的问题是,它只将数据发送到当前线程(从中接收)。
我找不到Python的线程间通信的好文档。
我的问题的任何解决方案,以便我可以向所有客户端发送数据。
感谢。
#!/usr/bin/env python
"""
A server with multithreading to handle multiple clients.
"""
import select
import socket
import sys
import threading
import logging
import datetime
class Server:
def __init__(self):
self.host = ''
self.port = 25000
self.backlog = 5
self.size = 1024
self.server = None
def open_socket(self):
try:
self.server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.server.bind((self.host,self.port))
self.server.listen(5)
lc.append(self.server)
except socket.error, (value,message):
if self.server:
self.server.close()
print "Could not open socket: " + message
sys.exit(1)
def run(self):
self.open_socket()
input = [self.server,sys.stdin]
running = 1
while running:
inputready,outputready,exceptready = select.select(input,[],[])
for s in inputready:
if s == self.server:
c = Client(self.server.accept())
c.start()
threads.append(c)
# close all threads
self.server.close()
for c in threads:
c.join()
class Client(threading.Thread):
def __init__(self,(client,address)):
threading.Thread.__init__(self)
self.client = client
self.address = address
self.size = 1024
dc[address[0]]=client#address[1]
logging.info('%s added successfully...',address[0])
def run(self):
running = 1
print dc
while running:
data = str(self.client.recv(self.size))
#print dc
if data.strip() == '0x01':
sendtoAll()
elif data.strip() == '0x02':
self.client.send("version"+data)
elif data.strip() == '0x03':#return current time
print datetime.datetime.now()
self.client.send(str(datetime.datetime.now()))
else:
self.client.send("empty")
#self.client.close()
#running = 0
def sendtoAll():
for i, sock in dc.items():
print "Address:Sockets = ", i,sock
try:
print "sending to %s by Thread "%i
sock.send("data"+str(threading.current_thread().getName()))
except socket.error,e:
print "error socket %s\n" % e
sock.close()
del lc[i]
if __name__ == "__main__":
dc={} #dict to store ip-address:scokets pair
lc=[] #tuples to store all sockets
threads=[] #holds threads
logging.basicConfig(level=logging.INFO)
logging.info('Starting Server Object...')
s = Server()
s.run()
客户端代码
import socket
import sys
host = '192.168.1.4'
port = 25000
size = 1024
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((host,port))
sys.stdout.write('%')
while 1:
# read from keyboard
line = sys.stdin.readline()
if line == '\n':
break
s.send(line)
data = s.recv(size)
sys.stdout.write(data)
sys.stdout.write('\n%')
s.close()
答案 0 :(得分:1)
您可以创建线程对象(如果有的话)iterable并创建一个“广播”函数,它只是遍历您的线程并使用它们的套接字发送信息。
或者如果你没有每个线程的对象,你总是可以只有一个套接字列表,并做几乎相同的事情。
确保根据需要正确使用锁(适用于所有套接字或每个插槽)
答案 1 :(得分:0)
TCP套接字是两个端点之一。 TCP中没有“广播”这样的东西。如果您想向所有客户发送一条消息,则必须将它们分别发送给每个客户。
如果您为所有客户端对象使用合适的容器,那么只需对此进行迭代即可,将消息发送给每个客户端。