Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Repo info
Activity
  • Mar 26 01:42
    dependabot[bot] labeled #559
  • Mar 26 01:42
    dependabot[bot] opened #559
  • Mar 26 01:42

    dependabot[bot] on npm_and_yarn

    Bump minimist from 1.2.5 to 1.2… (compare)

  • Mar 26 01:41
    dependabot[bot] labeled #558
  • Mar 26 01:41
    dependabot[bot] opened #558
  • Mar 26 01:41

    dependabot[bot] on npm_and_yarn

    Bump minimist from 1.2.5 to 1.2… (compare)

  • Mar 24 09:45
    DominicTobias commented #254
  • Mar 19 08:13
    herzi edited #557
  • Mar 18 17:12
    herzi opened #557
  • Mar 13 18:35
    Shankar-khati commented #556
  • Mar 11 12:29
    Shankar-khati closed #556
  • Mar 11 12:29
    Shankar-khati commented #556
  • Mar 11 12:17
    Shankar-khati closed #551
  • Mar 11 11:57
    Shankar-khati commented #556
  • Mar 10 16:50
    jondubois commented #556
  • Mar 10 16:50
    jondubois reopened #556
  • Mar 10 16:49
    jondubois commented #556
  • Mar 10 16:49
    jondubois closed #556
  • Mar 10 16:49
    jondubois commented #556
  • Mar 10 16:49
    jondubois commented #556
Coder of Salvation / Leon van Kammen
@coderofsalvation
question: does socketcluster also do long polling? (does it use socket.io under the hood?)
Muhammad Rehan Ali
@mrehanali
Hello everyone, does socketcluster recovers messages if a connection gets recovered after interruption?
AHBOUCH Amine
@matrixmonster11
Hello, I have implemented socketcluster with fastify, it works amazingly fine but I am looking for some advises for best practices to keep it as performant as possible. An example would be transmitPublish through a channel, should I close the channel after being used since it was created based on a document id?
Jonathan Gros-Dubois
@jondubois
@shawn2020:matrix.org I'm not familiar with it but I don't think so because SC implements its own JSON protocol.
@prakashru SC is based on WebSocket. You could run an SC server on a different port for each REST service, then the load balancer could send all WebSocket traffic to the port where the SC server is hosted. There are many, many ways to integrate though.
Jonathan Gros-Dubois
@jondubois
@coderofsalvation No. Some aspects of the SC protocol were inspired by Socket.io but it does not use socket.io. SC does not provide log polling fallback; it's a pure WebSocket solution; this is more elegant, scales better and is much more efficient.
@mrehanali No, SC does not have any message delivery guarantees but you can implement yourself relatively easily using message UUIDs and message receipts.
That said, if the socket starts out disconnected and you transmit a message, the socket will attempt to connect automatically (this is the default setting). But if it disconnects after the message has already been sent by the opposite side of the socket but before it has been received, it's still possible that the message could have been missed; that's why it's important to assign a UUID to each message and make the other side send you a receipt which contains that UUID so you can verify explicitly if the other side has received the message or retry otherwise (if you need delivery guarantees).
Jonathan Gros-Dubois
@jondubois

@matrixmonster11 If you're no longer interested in consuming messages from a specific channel, then you should invoke socket.closeChannel(channelName) or channel.close() on the client side; this will both unsubscribe the client from the channel and also break out of all for-await-of loops which are consuming the channel data (this will allow them to be garbage collected automatically on the client side). On the server-side, SC will garbage-collect any channel automatically as soon as it it reaches 0 subscribers...

It's also possible to unsubscribe from a channel temporarily by using socket.unsubscribe(channelName) or channel.unsubscribe() but this will keep all the consumer for-await-of loops active and they will resume message processing until the socket is subscribed to the channel again using socket.subscribe(channelName)... Note that using unsubscribe will still cause the channel to be garbage collected on the server side (assuming it reaches 0 client subscribers) but the difference with socket.closeChannel is that unsubscribe doesn't fully cleanup on the client side; it's only useful if you intend to re-use the channel later.

The subscription and consumption of channel data are treated independently in SC.

Ehsan Mokhtari
@ehsanm94
Hi all,
Is there any best practice to connect two specific users to a same socket cluster worker? I’m using sc version 14
Jonathan Gros-Dubois
@jondubois

@ehsanm94 In most situations, trying to map users to specific workers is a bad idea as it creates a potential DoS attack vulnerability since an attacker could exploit the worker-selection/load balancing rules to target and saturate specific workers with connection requests and messages. A random load balancing algorithm is the most secure.

It's also better from a scalability point of view if you don't try to target specific workers. SC's pub/sub mechanism allows users to publish and subscribe to/from any worker in the cluster.

That said, if each worker serves a different purpose (e.g. a distinct game server with completely different players and data or a completely different service), then you might just want to associate each one with a different subdomain or URL.

Ideally, the SC server should be passive; it should service clients' needs. The client should be the one to tell the server what it needs; the server's only role is to enforce access control rules (e.g. is ClientA allowed to access ResourseB or ChannelC?) - To get good scalability, the server should avoid deciding what to do on behalf of the client.
Ehsan Mokhtari
@ehsanm94
@jondubois Thanks for your complete reply and mentioned tips.
Mario Koch
@KochMario
Hi all,
I'm wondering if there's any way to get all listeners / subscriptions in scc mode.
I.e. I'm currently running SocketCluster on Kubernetes with 3 worker instances, 2 brokers and 1 state.
I've tried with exchange.subscriptions(true) and clusterBrokerClient.getAllSubscriptions(), but they all seem to return only the subscriptions of the broker that's executing this command. However I'm interested in extracting all currently open subscriptions across all brokers.
KHIRANI
@web75018
Hi guys,
im looking for a way to connect socketcluster over TCP. thanks
apiscerena
@apiscerena
Hi all, any benchmark with ws or socket.io?
Bryan de Asis
@bryandeasis
Hello, I'm new here and reading about SC, I'm just wondering let say I have a 1 machine with 4 CPUs 16GB RAM and 5 GB Network, How many concurrent connection and subscribe to a channel can it handle? because I have a project that needs to handle at least 50,000 to 75,000 concurrent connections and chatting into the same channel. Thanks in advanced.
sachin shinde
@sacOO7
There would be a network card limit
for a single PC. Number of TCP connections cant exceed 64K
Bryan de Asis
@bryandeasis
Hi Sachin, Thank you for your response, I'll be hosting it at AWS, at least I just have an idea how much a single machine with 4CPUs and 16GB RAM and 5GB Network . I will also autoscale it with EC2s
Also, another question is, what are the ratios between the Broker and the Application it self?
Bryan de Asis
@bryandeasis
Application meaning including the server
sachin shinde
@sacOO7
I think @jondubois would be right person to answer this one
Bryan de Asis
@bryandeasis
ok @sacOO7 I'll wait for @jondubois answer, thanks
Jonathan Gros-Dubois
@jondubois

@josiahbryan Sachin makes a good point about host limits; there are a few limits which can be configured on the host. One of these is the file limit (which limits the number of open sockets). You should ensure that the host/Linux configs will support that amount of connections.

About SC itself, depending on your use case, it is possible to support 75K concurrent connections on a single server but it depends significantly on how often the average client publishes a message and how many subscribers each message reaches.

From a basic test I did a while ago; all clients were subscribed to the same channel and one client published a new message to this channel every 5 seconds (so this message would reach all clients). I found that a single process could comfortably handle 10K to 20K clients per process. So on a 4-core host, this would be between 40k to 80k clients.

The exact type of workload can have a huge impact on how many clients can be supported and how many scc-broker instances you will need. There are a lot of factors to consider. One of the main ones is whether the workload is publish-heavy or subscribe-heavy.

For subscribe-heavy workloads with many subscribers consuming messages from just a few publishers, you don't need many scc-brokers; in extreme cases, 1 broker may be enough to support tens of millions of subscribers (client-facing sc worker instances would be the bottleneck in this case). SC tries to minimize the number of messages which pass through the broker on the back end.

For publish-heavy workloads, you may need more scc-broker instances. As a rough guideline, I aim to keep the number of messages which pass through each scc-broker process to below 10K messages per second. SCC shards different channels across available scc-broker instances using a consistent hashing algorithm which gives a random distribution; the more channels you have, the more even the distribution is.

Jonathan Gros-Dubois
@jondubois
You can read this article I wrote a while back for more detailed info: https://hackernoon.com/socketcluster-scalability-considerations-1b3355ab2fd8
Bryan de Asis
@bryandeasis
Great ill read through it, Thanks a lot for the idea
Bryan de Asis
@bryandeasis
@jondubois So, do you think, autoscaling SCBroker and the Application/Server will handle? including the concurrent connections and its count? and will the (1 server) State Server can handle that 80K concurrent connections?
muhamadshalaby
@muhamadshalaby
Hi, I'm new here, I installed SC in cluster mode, I have 2 workers, some clients sessions connected to worker1 and some other clients sessions connected to worker2, is there any way to get all connected sessions in all workers?
Jonathan Gros-Dubois
@jondubois

@bryandeasis Yes it can autoscale. As you add and remove scc-broker and scc-worker instances, the channel sharding gets adjusted automatically.

Clients do not connect to the scc-state instance so it is not a bottleneck for scalability. A single scc-state server should be able to comfortably connect to over 1K scc-worker and scc-broker instances... If you assume that each scc-worker can handle 20K connections, this is 20K * 1K= 20 million concurrent connections.

@muhamadshalaby You could get a list of all clients on each server using the clients poperty https://socketcluster.io/docs/api-ag-server/#properties and then have each server send them to a central place... But this approach won't scale. Beyond a certain number of clients, it's physically impossible to have all the data in a single place because it will be too much data.
Jonathan Gros-Dubois
@jondubois
If you want to run analytics at scale, you will need to design your algorithm to perform partial computation on each process and then only combine the results in a central process/database.
Bryan de Asis
@bryandeasis
@jondubois, @sacOO7 and everyone here, thank you so much for your prompt response, appreciate it so much, great support kudos to you guys, again thank you so much
muhamadshalaby
@muhamadshalaby

@jondubois thank you very much for your help and support, I have another concern, how to know if a specific user or group of users are connected to the SC Cluster or not by using user id?
I can store the user status in Redis, if the user emit the login event and succeeded to login, i will mark this user as online, and if the user disconnected i will mark him as offline, but if the SC worker goes down or crashed, how to mark all the connected users to the crashed SW worker as offline users?

please help.

Jonathan Gros-Dubois
@jondubois
@muhamadshalaby if using something like Redis, you would need to update the last activity timestamp for each user on an interval and use that to determine if a user is online or offline. You should run a job in the background to cleanup stale sessions (where the last activity timestamp is too old) so that your Redis memory gets cleaned up.
You could make the interval like once per minute for each user
and if the last activity timestamp is older than 2 minutes, then you can say that they are offline (so you add some safety margin)
I also wrote a module some time ago which implements presence in a stateless way without relying on Redis: https://www.npmjs.com/package/sc-stateless-presence
Jonathan Gros-Dubois
@jondubois
The stateless presence plugin is optimized for smaller channels with up to 100 concurrent users. It can likely also handle channels with 1000 users but it's most efficient if the majority of channels in your system have less than 100 users online at the same time.
Jonathan Gros-Dubois
@jondubois
The plugin is actually quite efficient and could potentially be configured to handle channels with multiple thousands of users by lowering the presenceInterval - You trade accuracy to support more users
the default accuracy is 10 seconds
so it takes a little bit over 10 seconds to detect that a user has gone offline.
If you want channels with 1000 users on average, you may want to increase it 60000 (60 seconds) or more.
It can be just as efficient or even more efficient than a Redis solution depending on your use case and it's a lot easier to maintain since it doesn't require any cleaning up
and doesn't require a separate redis server
also it's extremely scalable
since it scales with SC
and you don't need to worry about scaling a Redis cluster
muhamadshalaby
@muhamadshalaby
@jondubois thank you very much for your help and support, i will try to use the stateless presence plugin.