Cannot get "redirect scheme" to work in backend section


#1

Hi, I have a haproxy cluster with two frontends for http and https and many backends which are selected using a domain2backend map.

Some of the backends must be accessed only through HTTPS.

I tried using redirect scheme https code 301 if !{ ssl_fc } in those backends but haproxy seems to be ignoring it.

Configuration excerpt:

global
   maxconn 1024
   debug
   log /sidecar/log local0 debug
   stats socket /var/run/haproxy.sock mode 600 level admin
   stats timeout 2m

defaults
    balance roundrobin
    maxconn 32
    log global
    monitor-uri /haproxy_test

frontend http-in
    bind *:80
    mode http
    option httplog
    option forwardfor
    use_backend %[req.hdr(host),lower,map_dom(/usr/local/etc/haproxy/domain2backend.map)]

frontend https-in
    bind *:443 ssl crt /usr/local/etc/haproxy/ssl
    mode http
    option httplog
    option forwardfor
    http-request add-header X-Proto https if { ssl_fc }
    use_backend %[req.hdr(host),lower,map_dom(/usr/local/etc/haproxy/domain2backend.map)]

backend redmine_www
    redirect scheme https code 301 if !{ ssl_fc }
    server 10.19.12.253:5200 10.19.12.253:5200 check
    server 10.19.11.197:5200 10.19.11.197:5200 check
    server 10.19.13.150:5200 10.19.13.150:5200 check

I am using haproxy version 1.7.3

/ # haproxy -vv
HA-Proxy version 1.7.3 2017/02/28
Copyright 2000-2017 Willy Tarreau <willy@haproxy.org>

Build options :
  TARGET  = linux2628
  CPU     = generic
  CC      = gcc
  CFLAGS  = -O2 -g -fno-strict-aliasing -Wdeclaration-after-statement
  OPTIONS = USE_ZLIB=1 USE_OPENSSL=1 USE_LUA=1 USE_PCRE=1

Default settings :
  maxconn = 2000, bufsize = 16384, maxrewrite = 1024, maxpollevents = 200

Encrypted password support via crypt(3): yes
Built with zlib version : 1.2.8
Running on zlib version : 1.2.8
Compression algorithms supported : identity("identity"), deflate("deflate"), raw-deflate("deflate"), gzip("gzip")
Built with OpenSSL version : OpenSSL 1.0.2k  26 Jan 2017
Running on OpenSSL version : OpenSSL 1.0.2k  26 Jan 2017
OpenSSL library supports TLS extensions : yes
OpenSSL library supports SNI : yes
OpenSSL library supports prefer-server-ciphers : yes
Built with PCRE version : 8.39 2016-06-14
Running on PCRE version : 8.39 2016-06-14
PCRE library supports JIT : no (USE_PCRE_JIT not set)
Built with Lua version : Lua 5.3.3
Built with transparent proxy support using: IP_TRANSPARENT IPV6_TRANSPARENT IP_FREEBIND

Available polling systems :
      epoll : pref=300,  test result OK
       poll : pref=200,  test result OK
     select : pref=150,  test result OK
Total: 3 (3 usable), will use epoll.

Available filters :
	[COMP] compression
	[TRACE] trace
	[SPOE] spoe

I have been looking for a solution and trying different options without any success.

I would appreciate any help.

Thanks.

P.S. Also in StackOverflow: http://stackoverflow.com/questions/42699540/haproxy-redirect-scheme-in-backend-not-working


#2

The redirect would probably work, but I don’t think the variable ssl_fc is available in a backend.

Can you verify if it works without the “if !{ ssl_fc }”?

Try accessing the X-Proto header, like
redirect scheme https code 301 if !{ hdr(X-Proto) -m str https }


#3

Hi Lukas, thanks for your time,

I have just tried without the condition and it does not work.

backend redmine_www
    redirect scheme https code 301
    server localhost:3000 127.0.0.1:3000 check

The documentation says that redirect scheme can be used in the backend section. I am out of ideas.

Anything else I can try?


#4

Mmmh, I’m not sure what why this wouldn’t work. Can you try to force “mode http” in the backend?


#5

Thanks!!! That solved the issue!

Using mode http in the backend the “redirect” works as supposed. In fact, the variable ssl_fc is available in the backend as I can use if !{ ssl_fc}.

Thanks again for your time!


#6

Ok, great. I suggest putting “mode http” in the default section, that will fix all front and backends.


#7

I have one backend where I need to use mode tcp. I guess that’s the reason why I was not using mode http in the default section. I will review the docs to refresh how the mode keyword is used, defaults,…

Thanks again!.


#8

You can just define “mode tcp” where you need it, it will overwrite the “mode http” default.