HTTP/2 behind reverse proxy

2019-02-26 23:00发布

问题:

So far all the tutorials tell me that I need to enable SSL on my server to have HTTP/2 support.

In the given scenario, we have nginx in front of the backend Tomcat/Jetty server(s), and even though performance-wise it worth enabling HTTP/2 on the backend, the requirement to have HTTPS there as well seems to be an overkill.

HTTPS is not needed security-wise (only nginx is exposed), and is a bit cumbersome from the operational perspective - we'd have to add our certificates to each of the Docker containers that run the backend servers.

Isn't there a way around that provides HTTP/2 support all the way (or at least similar performance), and is less involved to set up?

回答1:

The typical setup that we recommend is to put HAProxy in front of Jetty, and configure HAProxy to offload TLS and Jetty to speak clear-text HTTP/2.

With this setup, you get the benefits of an efficient TLS offloading (done by HAProxy via OpenSSL), and you get the benefits of a complete end-to-end HTTP/2 communication.

In particular, the latter allows for Jetty to push content via HTTP/2, something that won't be possible if the backend communication is HTTP/1.1.

Additional benefits include less resource usage, less conversion steps (no need to convert from HTTP/2 to HTTP/1.1 and viceversa), the ability to fully use HTTP/2 features such as stream resetting all the way to the application. None of these benefits will work if there is a translation to HTTP/1.1 in the chain.

If Nginx is only used as a reverse proxy to Jetty, it is not adding any benefit and it is actually slowing down your system, having to convert requests to HTTP/1.1 and responses back to HTTP/2.

HAProxy does not do any conversion so it's way more efficient, and allows a full HTTP/2 stack with all the benefits that it brings with respect to HTTP/1.1.



回答2:

You don't need to speak HTTP/2 all the way through.

HTTP/2 primarily addresses latency issues which will affect your client->Nginx connections. Server to server connections (e.g. Nginx to Tomcat/Jetty) will presumably be lower latency and therefore have less to gain from HTTP/2.

So just enable HTTPS and HTTP/2 on Nginx and then have it continue to talk HTTP/1.1 to Tomcat/Jetty.

There's also a question of whether everything supports HTTP/2 all the way through (e.g. Nginx proxy_pass directive and Tomcat/Jetty), which again is less of an issue if only using HTTP/2 at the edge of your network.