我在Python中有一个简单的PUSH/PULL
ZeroMQ代码。它看起来像下面。
def zmqtest(self):
print('zmq')
Process(target=start_consumer, args=('1', 9999)).start()
Process(target=start_consumer, args=('2', 9999)).start()
ctx = zmq.Context()
socket = ctx.socket(zmq.PUSH)
socket.bind('tcp://127.0.0.1:9999')
# sleep(.5) # I have to wait here...
for i in range(5):
socket.send_unicode('{}'.format(i))
问题是我必须在发送消息之前等待 .5 秒,否则只有一个消费者进程可以收到消息。如果我等待超过0.5秒,一切都很好。
我想在套接字绑定之前需要一段时间来安定下来,并且它是异步完成的。
我想知道是否有更可靠的方法来了解套接字何时准备就绪。
答案 0 :(得分:1)
首先让我们损坏术语。
ZeroMQ是一个很棒的框架。每个分布式系统的客户端都愿意使用它(除了仅使用inproc://
传输类),首先实例化异步数据抽取引擎.. { {1}} 实例,根据需要。
每个可扩展的正式通信模式Context()
执行不创建套接字,
但
而是稍后实例化一个访问点,可能稍后{ PUSH | PULL | ... | XSUB | SUB | PAIR }
或.connect()
到某个对方(某个.bind()
实例中的另一个适当类型的访问点,无论是否为本地(再次,本地 - Context()
- 只有基础设施是此规则的已知例外)。)
从这个意义上说,问题的答案" 当套接字准备好了吗?"需要进行端到端的调查"跨越"处理所有元素的分布式系统,参与套接字 - 类似行为的实现。
为此,您的代理可以自行连接接收访问点(作为 inproc://
原型),以便"嗅探",当local-end PULL
实例已达到RTO状态+ Context()
- 已创建的O / S L3 +接口开始分发预期的代理' s- .bind()
-ed message。
这部分可以进行间接或明确的测试。间接方式可以使用消息嵌入索引。这可能包含一个上升数字(序数),它带有关于订单的弱信息。鉴于PUSH
侧消息路由策略是循环法,本地代理可以确定,直到它的本地PUSH
- 接入点接收到指示连续序列的所有消息对于序数,在RTO状态中没有其他"远程" - PULL
- 代理。一旦"本地" PULL
- 接入点接收"间隙"在序数流中,这意味着(当然,只有在所有PULL
PUSH
- s设置正确的情况下)还有另一个 - 非本地< / strong> - .setsockopt()
- 处于RTO状态的代理。
也许是的,也许不是。关键是要更好地理解任何分布式系统必须以某种方式应对的新挑战。
多阶段消息队列的性质,多层实现(本地 - PULL
- 代理&#s;代码,本地PUSH
- 线程,local-O / S ,本地内核,LAN / WAN,远程内核,远程O / S,远程Context()
- 线程,远程 - Context()
- 代理&#39; s代码仅命名为很少)并且多代理行为只会引入许多地方,其中一个操作可能以其他方式获得延迟/阻塞/死锁/失败。
是的,在野外散步。
然而,人们可能会选择使用更丰富,更明确的信令(除了最初只考虑原始数据传输)并帮助解决多代理世界中特定于上下文的信令RTO感知行为,这可能更好地反映实际情况,并在分布式系统的非单一世界中开始出现的其他问题中存活下来。
明确的信号是应对的一种方式。
最近的API版本开始添加更多选项来微调特定用例的ZeroMQ行为。请务必仔细阅读可用于设置 PULL
-instance的所有详细信息,以调整套接字实例访问点行为,以便最符合您的分布式系统信令+传输需求:
Context()
还有更多。如果没有这些,设计将在现实世界交易的丛林中被钉入棺材。