ninenines / gun

HTTP/1.1, HTTP/2, Websocket client (and more) for Erlang/OTP.
ISC License
898 stars 231 forks source link

Ultra-high request volume #178

Closed 9mm closed 5 years ago

9mm commented 5 years ago

Hey,

I have an Elixir GenStage step that needs to hit 5 different XML data API hosts about 20,000 times per minute each (so 100K total requests in 1 minute, across 5 different hosts). I'd like to set some kind of timeout of 750ms or so, and ignore responses that return non-200 or time out.

I'm trying to figure out the best way to do this. All these API hosts support Keep-Alive, but I'm not sure about HTTP/2 (or if that would even help). Doesn't HTTP/2 require HTTPS (all of them don't have SSL)?

I'm wondering a few things before I spend days struggling with this 🗡

1) If Gun would be able to tackle this on one machine 2) Do you have any tips to achieve this goal? 3) How much would you guess HTTP/2 would help over HTTP/1.1 and keep-alive?

Thanks! Keep up the awesome work, this is a really nifty lib.

essen commented 5 years ago

To reach 100K over HTTP/1.1 connections you would probably need to have many connections per service. HTTP/1.1 requests are sequential and can't be canceled (to skip the body for example) without closing the connection and this has a fairly high cost. Try pooling and hope the services don't prevent you from opening enough connections I guess.

If even one service supports HTTP/2 then I would definitely try to use it to benefit from multiplexing, flow control, the ability to cancel requests and so on. HTTP/2 is not necessarily requiring TLS, there are 2 ways to establish an HTTP/2 connection over TCP: via the Upgrade mechanism and via Prior-knowledge where the client does the HTTP/2 handshake on the clear connection directly. I think Gun only supports the latter at the moment though. See https://tools.ietf.org/html/rfc7540#section-3 for the details.

The difference between HTTP/1.1 and HTTP/2 is huge especially for your scenario.

9mm commented 5 years ago

Awesome, thanks a ton. I'll give this a stab. As a side question, is that "Prior-Knowledge" piece automatic by Gun or do I need to 'do something'?

Also, I could just google this but if its quick to answer, how do I use this in an elixir project?

essen commented 5 years ago

Gun uses it automatically if the transport is plain TCP and the protocols option is set to [http2].

No idea about Elixir.

9mm commented 5 years ago

Thanks! Ill close this for now and if I run into any issues I'll just reach out again. Keep up the gr8 work