Load balancer for websockets - networking

I know how load balancers work for http requests. A client opens a connection with the LB, LB forwards the request to the backend servers, LB gets a response and from the same connection it sends the response to the client and closes the connection. I want to know the internal details of load balancer for websockets. How the connections are maintained and how the response is sent to the client. I read many questions on stackoverflow but none of them gave a clear picture of the internal implementation of LB

the LB just route the connection to a server behind it.
so as long you keep the connection open you will keep being connected to the same server and do not communicate with the LB again.
depending on the client, on reconnection you could be routed to another server.
I'm not sure how it works when some libraries fallback to JSON-P tho

Implementations of load balancers have great variety. There are load balancers that support websockets, like F5's BIG-IP (https://support.f5.com/kb/en-us/solutions/public/14000/700/sol14754.html), and LB's that I don't think support websocekts, like AWS ELB (there is a thread where somebody says they could make it with ELB but I suppose they added some other component behind ELB: How do you get Amazon's ELB with HTTPS/SSL to work with Web Sockets?.
Load Balancer's not only act as terminators of HTTP connections, they can terminate also HTTPS, SSL, and TCP connections. They can implement stickiness based on different parameters, like cookies, origin IP, etc. (like F5) In the case of ELB's they use only cookies, and it could be application generated cookies or LB generated cookies (both only with HTTP or HTTPS). Also stickiness can be kept for certain defined time, sometimes configurable.
Now, in order to forward data corresponding to websockets, they need to terminate, and forward, connections at level of SSL or TCP (not HTTP or HTTPS). Unless they understand websocket protocol (I don't know if any does it). Additionally, they need to keep stickiness to the server with which the connetion was opened. This is not possible with ELB but yes with more complex LB's like BIG-IP.

Related

Do HTTPS connections require HTTPS proxies or can I use HTTP proxies?

The question is about HTTP vs HTTPS.
If I want to anonymously load a website that forces HTTPS, like Google.com, do I need an HTTPS proxies, or can I get away with HTTP proxies?
If your proxy is SOCKS it will not care what kind of socket is connecting through it. It has its own handshake and it does not care about what happens after the handshake. Whether after the SOCKS handshake an SSL handshake (HTTPS) is started it is not a SOCKS proxy problem, it will just pass through.
Several HTTP proxies on the other hand expect HTTP headers to guide them, such a HTTP proxy will not allow HTTPS since it needs to read the headers.
On the third hand (ekhm... well, foot?), an HTTP proxy that supports HTTP CONNECT can also setup the transfer of arbitrary data. Therefore such a proxy can setup any type of socket, which can have an SSL handshake, which can then be used for HTTPS transfer.
HTTP Proxy Server supports CONNECT verb which supports HTTPS connections within HTTP Proxy. You don't need special HTTPS proxy server or any other setup.
CONNECT verb allows you to create binary socket tunnel to any given IP:Port address. So any HTTP client (all browsers), will open secure tunnel and communicate securely over proxy server. However, no one cant control or see anything that is going through the tunnel unless they implement man in middle attack by sending you self-signed certificates.
Most firewall these days automatically implement man in middle self signed certificates that are deployed in work network, so you have to probably dig more to identify whether it is really secure or not. So it may not be that anonymous.
If you're trying to access a service anonymously, you won't get this by running your own proxy. It's not clear from the original question what is meant by "proxy", e.g. local service, or remote service. You won't get anonymity by surfing through a proxy that's on your network, unless it's something like a TOR proxy which relays out through the TOR network.
As for whether proxies can support HTTPS or not, that's been covered here, it would be unusual to find a proxy that doesn't support CONNECT. However if it's a remote anonymizing service you're using, I doubt they would do MitM, since you'd need to install the signing cert into your trusted root store, so they couldn't do that surreptitiously.

Forward HTTP traffic with erlang

I want to write a "smart" load balancer, with "smart" I mean that it should route different request on different servers and ports based on the URL.
As example somehost.com/server1 should go to the server1 while somehost.com/server3 should go to the server3.
However I don't want my load balancer to establish the connection with the client, make the requests to the backend server, and the return to the client.
The load balancer should be as much transparent as possible.
The request should arrive to the backend servers and then return immediately to the client, without the need to go through the load balancer.
How is this achievable ? Are there example in erlang ?

Websockets situation - on port 80 or 443, websocket message doesn't go through

i'm having a problem with my app, on a certain situation.
We have a java server with jetty webserver embedded, and an air app on the client side.
It is working properly but on a single situation of a certain customer.
They have a private network that is not administrated by them (and has little chances of being changed as request). So, the only port they allow are 80 and 443.
The communications between the server and the client are through websockets and http.
The "online" check is made through http and, then, we use websockets to notify the client in order to start communication between them.
The thing is, in this situation, the "online" state works properly and any communication send by the client (forced), as it goes through http, gets to the server but, when the server communicates with the client, using websockets, it doesn't work.
We are using wireshark to check the communications: On a working setup, when the client app starts, a websocket is shown on wireshark, on the server side (registering the client on the server). And, after that, websockets that are only used from server to the client, don't show also.
What can be the problem? The port 80? (the same happens with 443 on that network).
Can it be a proxy/firewall that are blocking ws:// messages?
I've read somewhere that wss:// (encripted websockets) would work?
Thanks for your help.
Edit, so, I tried with https and wss communication and the same thing happens.. no websocket is set between the client and server (registering the client on the server).
This situation is happening for http on the customer network. On my test network, it works on http/ws but not with https/wss..
There are many firewalls and gateways out "in the wild" that do not understand the whole WebSocket HTTP/1.1 GET -> UPGRADE -> WebSocket mechanism.
There are several broken firewall implementations will attempt to interpret the WebSocket framing as improper content for HTTP/1.1 (which is a bad reading of the HTTP/1.1 spec) and start to muck with it.
The types of firewalls that inspect/filter/analyze the request/response contents are the ones that seem most susceptible.
I would check that the hardware (or software) that they are using to firewall their network is both compliant and upgraded to support WebSocket RFC-6455.

Proxy server basics

I'm learning about network programming. Specifically proxy servers. I've created a very rudimentary proxy server on my mobile phone. However I think there's some proxy server basics that I don't know that will help me create a more robust proxy server.
What I've done so far: server on my mobile device listens for requests from laptop. When server receives a request like www.google.com the web page contents are fetched and returned to the client on the laptop. The client then opens the page contents in a desktop browser.
I think the sending/receiving of requests can happen on a lower OSI model layer (perhaps transport). How can I create a more robust proxy server? (one that just sends and receives bytes and doesn't care/know about HTTP)
A proxy server runs at the same layer as the protocol being proxied. It seems you are talking about an HTTP proxy. HTTP runs over TCP, and so does an HTTP proxy.
Define 'more robust'. What have you done so far?
An HTTP proxy server is a pretty simple thing, unless it has elaborate logging, caching, etc. The basis of it is (1) something to recognize and action the GET/POST/PUT/CONNECT etc. commands and (2) thereafter just copying bytes in both directions simultaneously.

How do you load balance TCP traffic?

I'm trying to determine how to load balance TCP traffic. I understand how HTTP load balancing works because it is a simple Request / Response architecture. However, I'm unsure of how you load balance TCP traffic when your servers are trying to write data to other clients. I've attached an image of the work flow for a simple TCP chat server where we want to balance traffic across N application servers. Are there any load balancers out there that can do what I'm trying to do, or do I need to research a different topic? Thanks.
Firstly, your diagram assumes that the load balancer is acting as a (TCP) proxy, which is not always the case. Often Direct Routing (or Direct Server Return) is used, or Destination NAT is performed. In both cases the connection between backend server and the client is direct. So in this case it is essentially the TCP handshake that is distributed amongst backend servers. See the following for more info:
http://www.linuxvirtualserver.org/VS-DRouting.html
http://www.linuxvirtualserver.org/VS-NAT.html
Obviously TCP proxies do exist (HAProxy being one), in which case the proxy manages both sides of the connecton, so your app would need to be able to identify the client by the incoming IP/Port (which would happen to be from the proxy rather than the client). The proxy will handle getting the messages back to the client.
Either way, it comes down to application design as I would imagine the tricky bit is having a common session store (a database of some kind, or key=>value store such as Redis), so that when your app server says "I need to send a message to Frank" it can determine which backend server Frank is connected to (from DB), and signal that server to send it the message. You reduce the problem of connections (from the same client) moving around different backend servers by having persistent connections (all load balancers can do this), or by using something intrinsically persistent like a websocket.
This is probably a vast oversimplification as I have no experience with chat software. Obviously DB servers themselves can be distributed amongst several machines, for fault-tolerance and load balancing.

Resources