slact / nchan

Fast, horizontally scalable, multiprocess pub/sub queuing server and proxy for HTTP, long-polling, Websockets and EventSource (SSE), powered by Nginx.
https://nchan.io/
Other
3.01k stars 292 forks source link

Issue with nchan and Android clients #636

Open SimonFair opened 2 years ago

SimonFair commented 2 years ago

Currently I have noticed that the number of stored messages increases until memory is exhausted, issue is from Android clients and then selecting another tab in the client browser. Tried to set expiry for messages but then dont seem to get purged.

#
# Listen on local socket for nchan publishers
#
server {
    listen unix:/var/run/nginx.socket default_server;
    location ~ /pub/(.*)$ {
        nchan_publisher;
        nchan_channel_id "$1";
        nchan_message_buffer_length $arg_buffer_length;
        nchan_message_timeout 15s;
    }
    location ~ /nchan_stub_status$ {
        nchan_stub_status;
    }
}

Every 1.0s: curl --unix-socket /var/run/nginx.socket http://localhost/nchan_stub_status computenode: Sun Mar 20 13:48:47 2022

% Total % Received % Xferd Average Speed Time Time Time Current Dload Upload Total Spent Left Speed 0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0 100 384 100 384 0 0 3289k 0 --:--:-- --:--:-- --:--:-- 375k total published messages: 42200 stored messages: 1879 shared memory used: 14908K shared memory limit: 131072K channels: 27 subscribers: 9 redis pending commands: 0 redis connected servers: 0 total interprocess alerts received: 0 interprocess alerts in transit: 0 interprocess queued alerts: 0 total interprocess send delay: 0 total interprocess receive delay: 0 nchan version: 1.2.15

SimonFair commented 2 years ago

Any suggestions of ideas to try?

slact commented 1 year ago

How much shared memory does Nchan have? What is the message publishing rate and average size?

SimonFair commented 7 months ago

nchan has 131072K allocated.

When it is running as expected outstanding messages are low

total published messages: 323326 stored messages: 8 shared memory used: 72K shared memory limit: 131072K

Issue comes when an android device or similar is used on the page and the device goes stops processing the page, the messages start to build up to the point it exceeds the available memory. The subscriber is still connected.

I have tried add buffer length and timeout to the server but does not seem to make a difference.

  #
    # Listen on local socket for nchan publishers
    #
    server {
        listen unix:/var/run/nginx.socket default_server;
        location ~ /pub/(.*)$ {
            nchan_publisher;
            nchan_channel_id "$1";
            nchan_message_buffer_length 1;
            nchan_message_timeout 1s;
        }
        location ~ /nchan_stub_status$ {
            nchan_stub_status;
        }
    }

Message sizes are smallish around 4k

total published messages: 333099 stored messages: 462 shared memory used: 632K shared memory limit: 131072K channels: 15 subscribers: 8 redis pending commands: 0 redis connected servers: 0 redis unhealthy upstreams: 0 total redis commands sent: 0 total interprocess alerts received: 0 interprocess alerts in transit: 0 interprocess queued alerts: 0 total interprocess send delay: 0 total interprocess receive delay: 0 nchan version: 1.3.6

slact commented 6 months ago

What subscriber type do these devices use?

SimonFair commented 6 months ago

I guess you mean websocket?

var vmdashusage = new NchanSubscriber('/sub/vm_dashusage',{subscriber:'websocket'});

slact commented 6 months ago

Yes, thanks. What about the subscriber location block in your config?

SimonFair commented 6 months ago

#

Listen on local socket for nchan publishers

#
server {
    listen unix:/var/run/nginx.socket default_server;
    location ~ /pub/(.*)$ {
        nchan_publisher;
        nchan_channel_id "$1";
        nchan_message_buffer_length 1;
        nchan_message_timeout 1s;
    }
    location ~ /nchan_stub_status$ {
        nchan_stub_status;
    }
}
SimonFair commented 6 months ago

function publish($endpoint, $message, $len=1) { $com = curl_init("http://localhost/pub/$endpoint?buffer_length=$len"); curl_setopt_array($com,[ CURLOPT_UNIX_SOCKET_PATH => "/var/run/nginx.socket", CURLOPT_HTTPHEADER => ['Accept:text/json'], CURLOPT_POST => 1, CURLOPT_POSTFIELDS => $message, CURLOPT_RETURNTRANSFER => 1 ]); $reply = curl_exec($com); curl_close($com); if ($reply===false) my_logger("curl to $endpoint failed", 'publish'); return $reply; }

slact commented 6 months ago

That's the publisher location. I'm interested in the subscriber location, the one containing nchan_subscriber or nchan_pubsub.

SimonFair commented 6 months ago
    #
    # nchan subscriber endpoint
    #
    location ~ /sub/(.*)$ {
        nchan_subscriber;
        # nchan_authorize_request <url here>
        nchan_channel_id "$1";
        nchan_channel_id_split_delimiter ",";
    }
    location /nchan_stub_status {
        nchan_stub_status;
    }
SimonFair commented 5 months ago

@slact any suggestions on what to try?

slact commented 5 months ago

If your traffic permits it, please run Nchan with 1 worker process and see if that makes a difference.

SimonFair commented 5 months ago

If your traffic permits it, please run Nchan with 1 worker process and see if that makes a difference.

grep worker_processes /etc/nginx/nginx.conf worker_processes 1;