1

I am trying to make a c-program server that publishes images via nng, and a python client via pynng that subscribes to the images.

For some reason i cannot connect these 2 parts and I dont know why. C/C++-program compiles and runs fine and so does python program, but something is published on the C/C++-program, nothing is recieved on the python client. Client and server runs on the same machine. Here is my C/C++-code for the server:

#include <nng/nng.h>
#include <nng/protocol/pubsub0/pub.h>

int main(int argc, char* argv[]){

    nng_socket sock;
    int rv;
    const char *url = "tcp://0.0.0.0:2234";

    if ((rv = nng_pub0_open(&sock)) != 0) {
            fatal("nng_pub0_open", rv);
    }
    if ((rv = nng_listen(sock, url, NULL, 0)) < 0) {
            fatal("nng_listen", rv);
    }

    // camera setup code omitted

    while(1){
        INT r = IS_SUCCESS;
        char* frame =(char*) d.processNextFrame(50,r); // grab image. if not successful, continue loop
        if (r != IS_SUCCESS || !frame)
            continue;

        std::cout << "frame caught... "<< bpp * nImgW * nImgH<< std::endl;

        if ((rv = nng_send(sock, frame, bpp * nImgW * nImgH, 0)) != 0) {
            fatal("nng_send", rv);
        }else{
            std::cout << "Frame Sent... "<< std::endl;
        }
    }
}

Here is my python code for the client:

from pynng import Sub0, Timeout
address = 'tcp://127.0.0.1:2234'
sub2 = Sub0(dial=address, recv_timeout=5000)
print(sub2.recv())

Can someone help me understand why this is not working?

Michael Hansen
  • 237
  • 2
  • 8

1 Answers1

1

You have to subscribe to topics on your subscribing socket, or you won't receive anything. In order to receive all messages, subscribe to the empty string:

from pynng import Sub0, Timeout
address = 'tcp://127.0.0.1:2234'
# note the additional keyword argument, topics:
# =============================================
sub2 = Sub0(dial=address, recv_timeout=5000, topics=b'')
print(sub2.recv())

Here are the pynng docs for Sub0.

I'm the creator of pynng. It would probably be nice to be clear in the docs that not subscribing to anything means you'll never receive anything; this is a common point of confusion.

Cody Piersall
  • 8,312
  • 2
  • 43
  • 57
  • Hi, i see that works if i set sub2 = Sub0(dial=address, recv_timeout=5000, topics=b'') But only if i send a simple message like this: std::string tstdata("msg"); if ((rv = nng_send(sock, (void*)tstdata.c_str(), 3, 0)) != 0) If i send the large array as shown above it does not work. Should i add something additional to make that work? – Michael Hansen May 08 '20 at 16:26
  • 1
    How large is "large"? nng used to drop messages larger than 1 MB by default, and I can't remember if the latest pynng keeps that behavior. More recent nng releases allow any message by default now, and future pynng will too. – Cody Piersall May 08 '20 at 18:02
  • 1
    You can set `recv_max_size` to `0` on the sub socket to accept any size of message. – Cody Piersall May 08 '20 at 18:05
  • i am trying to send 5044624 bytes per message – Michael Hansen May 08 '20 at 19:47
  • So setting `recv_max_size = 0` on the sub socket should solve that issue. – Cody Piersall May 08 '20 at 20:06
  • Maybe it would be a good idea to show in a warning that the message is discarded instead of silently discarding it? – Michael Hansen May 08 '20 at 20:18
  • This has been discussed on the [nng issue tracker](https://github.com/nanomsg/nng/issues/954) and led to a new default, which is to *not drop messages*. pynng just hasn't been updated yet :-). I remember losing a lot of time the first time I hit this problem with the legacy nanomsg library. Oh, the pain. – Cody Piersall May 08 '20 at 20:50