Skip to main content

Sockets

ZeroMQ is a library of sockets that talk to each other directly: no server, nothing stored, and a pattern that decides who receives each message.

The three socket patterns: a pipeline, a broadcast filtered by prefix, and requests told apart by connection, with no server between the peersPUSH/PULL: a pipelinePUB/SUB: a broadcastDEALER/ROUTER: request and replyVentilator: PUSHbindsWorker 1PULL, dialsgets 1 and 4Worker 2PULL, dialsgets 2Worker 3PULL, dialsgets 3Sink: PULL, bindsreads them in turnPublisher: PUB, bindsmatches the filtersSUB, dialsfilter jobs.SUB, dialsfilter pricesorders.new:no filtermatches, droppedResponder: ROUTER, bindsan identity per connectionRequester: DEALERdialsRequester: DEALERdials
The diagram as text
  1. PUSH/PULL: a pipeline: Ventilator: PUSH binds; Worker 1 PULL, dials gets 1 and 4; Worker 2 PULL, dials gets 2; Worker 3 PULL, dials gets 3; Sink: PULL, binds reads them in turn
  2. PUB/SUB: a broadcast: Publisher: PUB, binds matches the filters; SUB, dials filter jobs.; SUB, dials filter prices; orders.new: no filter matches, dropped
  3. DEALER/ROUTER: request and reply: Responder: ROUTER, binds an identity per connection; Requester: DEALER dials; Requester: DEALER dials
  4. Ventilator: PUSH binds → Worker 1 PULL, dials gets 1 and 4: in turn
  5. Ventilator: PUSH binds → Worker 2 PULL, dials gets 2
  6. Ventilator: PUSH binds → Worker 3 PULL, dials gets 3
  7. Worker 1 PULL, dials gets 1 and 4 → Sink: PULL, binds reads them in turn
  8. Worker 2 PULL, dials gets 2 → Sink: PULL, binds reads them in turn
  9. Worker 3 PULL, dials gets 3 → Sink: PULL, binds reads them in turn
  10. Publisher: PUB, binds matches the filters → SUB, dials filter jobs.: jobs.done
  11. Publisher: PUB, binds matches the filters → SUB, dials filter prices: prices.eur
  12. Publisher: PUB, binds matches the filters → orders.new: no filter matches, dropped
  13. Requester: DEALER dials → Responder: ROUTER, binds an identity per connection: identity A
  14. Requester: DEALER dials → Responder: ROUTER, binds an identity per connection: identity B

Every box in the picture is a socket in some process. A message goes from one socket to another over a connection between them. Nothing keeps it after that, so a socket that is not connected at the time never sees it.

Which side listens and which side dials is independent of which way messages flow. The stable part of a topology binds, and the parts that come and go dial it. In the pipeline the ventilator and the sink bind, and the workers dial both. A ZmqEndpoint states the side this service takes.

A PUSH socket deals its messages to its connected peers in turn, one message to one peer. A PULL socket reads from all of its peers in turn, so no peer starves the others. This is ZmqQueue.

A SUB socket sends its filters to the PUB it is connected to. The PUB compares the first frame of each message with every filter by prefix and sends the message only where one matches. A message no filter matches is dropped, and the publisher is not told. This is ZmqFanout, where a subscription's name is its filter.

A ROUTER socket gives each connection an identity. It puts the identity in front of every message it receives, and it sends a message to the connection whose identity is the first frame. A DEALER sends and receives with no identity frame. This is ZmqRpc, and Frames draws the envelope.

A socket may have many peers, and order holds between one pair of sockets only. ruststream-zeromq runs on tcp:// and ipc://. Another scheme is refused when the broker connects, before any socket opens.

The patterns are ZeroMQ's own (pipeline, publish-subscribe, request-reply), and the zguide explains which side binds.