Reputation: 1074
I'm running a SSE server on a VPS and it works perfectly, no problems at all, but due to scalability reasons I needed to move it to another server.
I moved the server to Google Cloud Platform/Google Container Engine and Kubernetes/Ingress. But now I've encountered that I can't keep a SSE connection effectively, it's completely unstable and it closes connections by itself.
Is there anything special I have to do to run a SSE server over Kubernetes/Ingress?
I assume my code/software runs perfect and that is not the issue, due it works perfectly in Kubernetes, VPS, on my machine, everywhere, just not when I add the Ingress configuration, and I'm doing this because I want HTTPS over the Kubernetes load-balancer.
Upvotes: 3
Views: 3739
Reputation: 1
you can solve this by a pubsub pattern. I use redis pubsub.
Example: (adding to your example)
Msg-1 from user 1 is sent to pod1 on node1. This message is then sent to a topic in redis. Every pod on every node is listening/subscribing on this topic (called publish/subscribe). Msg-1 will then be available on all pods at the same time. Each pod will then try to broadcast the Msg-1 as a "Server Sent Event" to all it's registered sinks (sse-connections).
Upvotes: 0
Reputation: 2886
I'ts not possible to do it, it may work for some clients and not for others, the explanation of this is with how kubernetes behave,
let's supposed there are 3 nodes in your app, a node is virtual machine, when a request it's being made, kubernetes has to decide in which of this virtual machines will run, if it's the case of SSE this conection must persists until client close your app, so with this in mind, let's supossed you have a chat app.
So we have two clients, now let's supossed kubernetes always redirect client 1 and 2 to node 1
when a SSE connection(green line) is stablished, this will persists, now let's supossed client 1 send a message, as I said before we are in the case everything goes through node 1,
the node will handle this request, your app will look in memory if receiver is connected and if so, it will send the message through SSE conection
in this case everything works perfect, the problem is when the clients are not redirected to the same node
when a client sends a message,
this will go through to node 1 but when checking if client 2 is connected, it won't find the conection because this connection was not saved in this node so the client 2 won't recieve this message. To solve this problem you will need a new structured, you need to have one instance dedicated only for SSE conections, so when a client conects to a sse it will go to a the dedicated instance
and when client 1 sends a message
the nodes will comunicate with this dedicated instance and will send to client 2 the message
now to created this dedicate server you should use and external source service if you want, or better you could create your own instance and redirect your sse endpoint to the SSE instance, you can do this with a Load Balancing this acts as a proxy and it will decide to which resource redirect based on the incoming URL more info Also you need to configure in this dedicate SSE server not to close connection to fast
Upvotes: 3
Reputation: 1074
Got it working by adding a long time on the timeout: 86,400 seconds. This is because it is a socket connection that needs to stay open and not a normal connection that would require less than 30 seconds to execute.
Upvotes: 4
Reputation: 27
I don't know what SSE means in that context, but yes, you need to setup correctly your Ingress Controller
to manage long standing session.
What type of Ingress
are you using ?
Upvotes: 0