zeromq is the same way. It's not a replacement for something like kafka or rabbitmq, it's a replacement for socket()
Some places you might use it: real-time financial data streams, multi-agent worker task/management, distributed database syncing. It’s basically a networking lib that makes common patterns easier. E.g send this message to everyone, list connected peers, handle these messages this way if the peer can’t take the message, and so on. They support doing this in a bunch of languages over a bunch of communication protocols.
Now all the Async/coroutine/ipc verbiage is mostly just because synchronization is a communication problem which is what zeroMQ happens to solve as well.
It hides the scalability problem of having many TCP sockets without solving it (e.g. pub-sub over TCP).
It does not solve the ahead-of-line blocking issue.
It requires reading a lot of documentation and doing experiments to find out what is the right combination of " fan-out, pub-sub, task distribution, and request-reply" that you have to use.
e.g. https://zguide.zeromq.org/docs/chapter4/ https://zguide.zeromq.org/docs/chapter5/ https://zguide.zeromq.org/docs/chapter3/
Plus a lot of "magic" happening in the library involves queues that you have no control over. You get applications that hang and fill buffers instead of failing early.
I suspect this is the reason why it never became a new layer in the TCP/IP stack
It does bring some nice things to the table, but using it has always felt at least a little bit "weird" to me. The docs are a little weird, and there are random caveats sprinkled around the library (e.g. you don't need to synchronize the startup of dependent services like described above, unless you were using certain transports in older versions and so on).
It used to be marketed somewhat towards developing multi-threaded applications, but it was always rather unclear what exactly the advantage of using, for example, the comparatively slow PUSH/PULL socket (ipc:// are pipes) over a MPMC (or as needed) queue ought to be.
It is also marketed towards resilient distributed apps, but, perhaps I was holding it wrong, but it'd always behave much like TCP and stuff like REQ/REP would pretty much always block forever if the peer goes away, while stuff like PUSH/PULL isn't reliable when peers go away, so for a distributed app these can't really be used anyway. So for this use case it always seemed rather too low-level and its guarantees too weak / non-applicable.
unless you tell it to do otherwise, that's exactly what it will do. The guide covers this: 4. Reliable Request-Reply Patterns
I had exactly the same (disappointing) experience.
zmq appears to be a layer that tries to hide some of the most important details that the socket layer exposes. socket programming and the state machines that tend to go along with it are some of the least difficult parts of systems programming to do well, it is well documented, well understood and there are ample tools to help measure ground truth. it was always weird to me that zmq had such a strong reputation; it basically hides what would otherwise be a few hundred lines of library code (including a framer).
ZeroMQ is not an out-of-the-box MQ solution. It takes some work to understand and build a functional MQ solution with ZeroMQ. If you want something that works out of the box I recommend RabbitMQ.
Are there are any, preferably open source, message queue based messaging systems using ZeroMQ?
It also allows one machine to broadcast a message to a 'topic' that other machines listen for.
Many other things. It's not perfect, but it Just Works.
”ZeroMQ (also spelled ØMQ, 0MQ or ZMQ) is a high-performance asynchronous messaging library, aimed at use in distributed or concurrent applications. It provides a message queue, but unlike message-oriented middleware, a ZeroMQ system can run without a dedicated message broker.”
I read it as a low-level abstraction for when you want to build a custom messaging infrastructure.
I prefer the “replacement for socket” pitch, personally.
Like you can tell it to use sockets if the machines are remote, or different inter-process communication if they're running on the same machine, etc.
It also has some common patterns like pub/sub and others.
A lot of people these days might use something like flink or spark to build a pipeline whereas I'd prefer to write a number of small servers with various fan out or fan in operations, broadcast style operations, request/reply semantics etc where appropriate
Makes way more sense and much simpler to my mind and allows much better control over performance characteristics.