peer.py
import zmq
import time
if __name__ == '__main__':
context = zmq.Context()
socket = context.socket(zmq.PUB)
while True:
print "I: Publishing"
socket.bind("tcp://*:5555")
socket.send_multipart(['general', 'Unique peer information'])
socket.unbind("tcp://*:5555")
time.sleep(1)
扫描仪.py
import zmq
if __name__ == '__main__':
context = zmq.Context()
socket = context.socket(zmq.SUB)
socket.setsockopt(zmq.SUBSCRIBE, 'general')
socket.connect("tcp://localhost:5555")
print "I: Scanning 5555"
while True:
message = socket.recv_multipart()
print "I: Receiving: {}".format(message)
我正在尝试在同一台计算机上通过同一端口广播多个对等点,并让一个“扫描器”监听并“查看”谁可用。每个对等方都会广播其联系信息,然后客户端会使用扫描仪找出谁有空,然后使用广播的信息通过 REQ/REP channel 进行连接。
为了完成这项工作,我尝试快速绑定(bind)一个 PUB 套接字,广播有关对等点的信息,然后解除绑定(bind),以便让其他对等点在不同时间绑定(bind)到同一套接字,并广播不同的集合下一个对等点的标识符。
我怀疑消息在发送之前由于解除绑定(bind)而被丢弃(调用 close()
时也会发生同样的情况)但我不知道如何将其清空关闭连接之前的队列,以免丢弃任何消息。
有什么想法吗?
- Windows 8.1 x64
- Python 2.7.7 x64
- PyZMQ 4.0.4
编辑
我在 ZMQ 邮件列表上问了同样的问题并得到了一些有趣的回复,请看这里:http://lists.zeromq.org/pipermail/zeromq-dev/2014-June/026444.html
最佳答案
订阅者必须连接到发布者才能接收任何消息。操作顺序必须类似于以下内容:
- 启动发布者(“开始”意味着定义套接字并绑定(bind)或连接它,对于订阅者,订阅你想要的消息。
- 启动订阅者(1 和 2 可以按任何顺序发生)
- 发送/接收您的消息
- 让一切都变慢
PUB
套接字是非阻塞的,它们不会等到有订阅者要发送给它,它只会在队列中移动它,如果订阅者不在等待它,它会丢弃它。 Check out the pyzmq pub/sub examples ,您会看到订阅者必须在发布者可以发送消息并知道消息将被接收之前宣布自己。
如果您知道您的订阅者将始终在指定的时间段内可用,您可以使用超时来伪造它,否则发布/订阅将不适合您。
所以,发生的事情是您的 PUB
套接字已绑定(bind),但您的订阅者连接需要非零时间,即使您先启动它,所以它还没有准备好你发送消息。消息被丢弃,然后您停止一切,仍然可能在订户有机会完全连接之前。
您将需要使用不同类型的套接字对,可能是 rep/req
,但您正在寻找将保留消息直到接收方准备好接收消息的阻塞行为。这可能意味着使用中央服务器来控制有关哪些对等点可用的信息,而不是尝试将信息广播给所有对等点,或者根据您的消息传递需求和体系结构进行其他操作。或者,您需要一个生命周期更长的发布/订阅系统。
关于python - 绑定(bind)、发布、解除绑定(bind)、重复,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24323124/