HTTP/2 SSL Offloading with Hitch and Varnish

HTTP/2 SSL Offloading with Hitch and Varnish

Since Chrome browsers showing you insecure warning on unencrypted websites soon, i will show you in this post how to setup HTTP/2 SSL Offloading with Hitch and Varnish in few easy steps.

 

Prerequisites:

  • A working Varnish 5.1+ Setup with H2 and PROXY Protocol enabled
  • OpenSSL 1.0.2+ that supports ALPN
  • Functional Hitch Setup with alpn protos H2 enabled
  • Texteditor (vi, joe, nano) of your choice

 

1. We start with the Hitch Setup

Open your /etc/hitch/hitch.cfg and if not already done we first set secure SSL Ciphers and SSL Options which will give you an Grade A rating at SSLLabs:

ciphers = "ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-DSS-AES128-GCM-SHA256:kEDH+AESGCM:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-DSS-AES128-SHA256:DHE-RSA-AES256-SHA256:DHE-DSS-AES256-SHA:DHE-RSA-AES256-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:AES:CAMELLIA:DES-CBC3-SHA:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH-DSS-DES-CBC3-SHA:!EDH-RSA-DES-CBC3-SHA:!KRB5-DES-CBC3-SHA"
tls-protos = TLSv1.0,TLSv1.1,TLSv1.2
prefer-server-ciphers = on
sni-nomatch-abort = on

2. Now we add our frontent include pem file to our Hitch config

frontend = "[ReplaceWithYourPublicIP]:443+/etc/hitch/certs/combined.yoursite_cert.pem"

Notes: Change the Bind IP, Cert Location that it matches your Setup.

 

3. Our complete hitch.cfg should now look like this

frontend = "[ReplaceWithYourPublicIP]:443+/etc/hitch/certs/combined.yoursite_cert.pem"

ciphers = "ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-DSS-AES128-GCM-SHA256:kEDH+AESGCM:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-DSS-AES128-SHA256:DHE-RSA-AES256-SHA256:DHE-DSS-AES256-SHA:DHE-RSA-AES256-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:AES:CAMELLIA:DES-CBC3-SHA:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH-DSS-DES-CBC3-SHA:!EDH-RSA-DES-CBC3-SHA:!KRB5-DES-CBC3-SHA"

tls-protos = TLSv1.0,TLSv1.1,TLSv1.2

prefer-server-ciphers = on
sni-nomatch-abort = on

quiet = on

backend = "[127.0.0.1]:6086"    # 6086 is the default Varnish PROXY port.
workers = 2                     # number of CPU cores

daemon = on
#user = "nobody"
#group = "nogroup"

alpn-protos = "h2, http/1.1"

write-proxy-v2 = on             # Write PROXY heade

Note: Change workers that it matches your needs.

 

4. In the final step we will prepare Varnish to speak the PROXY and HTTP/2 Protocol

Open /etc/default/varnish and extend the lines by PROXY and feature=+http2 like shown bellow:

DAEMON_OPTS="-a ReplaceWithYourPublicIP:80 -a 127.0.0.1:6086,PROXY 
             -T 127.0.0.1:6082 
             -f /etc/varnish/YourVCL.vcl 
             -p feature=+http2 
             -p thread_pools=2 
             -p thread_pool_min=450 
             -p thread_pool_max=5000 
             -p syslog_cli_traffic=off 
             -t 120 
             -S /etc/varnish/secret 
             -s malloc,1G"

Modify your VCL and add the redirects to force HTTPS

Right after vcl 4.0; line at the beginning of your vcl we enable std module first using: import std;

sub vcl_recv {
    
    # set x-forwarded-proto header to https if connections comes from Hitch SSL Proxy.
    if (std.port(local.ip) == 6086) {
        set req.http.X-Forwarded-Proto = "https";
    }
    
        # force http://www.ispire.me to https://www.ispire.me if connections comes from HTTP (Port: 80) Listener.
        if ( req.http.host ~ "^(?i)www.ispire.me" &&
        req.http.X-Forwarded-Proto !~ "(?i)https") {
                set req.http.x-redir = "https://www.ispire.me" + req.url;
                return(synth(301));
        }

        # force http://ispire.me to https://www.ispire.me.        
        if ( req.http.host ~ "^(?i)ispire.me") {
                set req.http.x-redir = "https://www.ispire.me" + req.url;
                return(synth(301));
        }
}

sub vcl_synth {
    if (resp.status == 301) {
        set resp.http.Location = req.http.x-redir;
        return (deliver);
    }
}

sub vcl_hash {
    # Cache https seperately
    if (req.http.X-Forwarded-Proto) {
        hash_data(req.http.X-Forwarded-Proto);
    }
}

Restart your Hitch and Varnish service and check your Logs for Errors.

Watch your Varnishncsa Access Log, Connections with HTTP/2 should contain “HTTP/2.0” and Fallback Clients: HTTP/1.1 now.

If all looks fine enjoy your new HTTP/2 capability!

If you are 100%ly sure that SSL setup is working, activate HSTS:

sub vcl_deliver {

set resp.http.Strict-Transport-Security = "max-age=31536000";
}
Rating: 5.0/5. From 6 votes.
Please wait...
Jules

Jules

Jules is the owner and author of ISPIRE.ME. He's a Linux System Engineer, Tech fanatic and an Open Source fan.

You may also like...

10 Responses

  1. Hu Hu says:

    Thank you!

    I have an error when changing vcl:
    Message from VCC-compiler:
    Symbol not found: ‘std.port’ (expected type BOOL):
    (‘/etc/varnish/default.vcl’ Line 55 Pos 9)
    if (std.port(local.ip) == 6086) {
    ——–########———————

    Running VCC-compiler failed, exited with 2
    VCL compilation failed

    I am using varnish 5.2.

    Something changed in 5.2?

    Thank you.

    Rating: 5.0/5. From 1 vote.
    Please wait...
    • Jules Jules says:

      You have to enable std module first:
      import std;
      Put it right after vcl 4.0; in your vcl.

      Rating: 5.0/5. From 2 votes.
      Please wait...
  2. Hu Hu says:

    Hello,

    Do you have an idea on enable server push (on WordPress)?

    I have successful installed varnish for https (thank you), I can see it is using http/2, but no push. I tried wordpress plugin for server push, no use.

    Thank you.

    No votes yet.
    Please wait...
    • Jules Jules says:

      You have to write your own HTTP/2 Server Push vcl since Varnish doesnt support Server Push nativetly.

      Reasons you can find here: https://varnish-cache.org/docs/trunk/phk/spdy.html

      Rating: 5.0/5. From 1 vote.
      Please wait...
  3. Hu Hu says:

    I am hunting half a day, there are no ready info, some are outdated.

    It is quite complicated for me: I have to wait someone else to write an updated version or a hint.

    No votes yet.
    Please wait...
  4. Hu Hu says:

    Hi, another question:

    I found http://domain.com redirected to https://domain.com

    But not http://www.domain.com to https

    Rating: 5.0/5. From 1 vote.
    Please wait...
    • Jules Jules says:

      have you checked and set everything like in the howto?

      See block: “Force http://www.ispire.me to https if connections comes from HTTP Listener.”
      That should redir http://www.ispire.me to https if http://www.ispire.me matches and x-forwarded-proto is NOT “https”.

      No votes yet.
      Please wait...
  5. Hu Hu says:

    Yes, only works in domain.com.

    Perhaps it is a bug of Varnish 5.2.0?

    No votes yet.
    Please wait...
    • Jules Jules says:

      On my setup it works fine with that settings.

      Rating: 5.0/5. From 3 votes.
      Please wait...
  6. Hu Hu says:

    Thank you, Jules, for offering personal help!

    It is ok now, due to my misconfiguration.

    If one day later, you install server push on ispire.me, please share it again, 🙂

    Many thanks again….

    Rating: 5.0/5. From 1 vote.
    Please wait...

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.