# Accept-proxy: stops working

**URL:** <https://discourse.haproxy.org/t/accept-proxy-stops-working/6774>\
**Category:** Help!\
**Created:** [August 2, 2021, 7:34am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774 "2021-08-02T07:34:57Z")\
**Posts on this page:** 14\
**Page:** 1

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 2, 2021, 7:34am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/1 "2021-08-02T07:34:57Z")

</div>

Hi Community.

When I adds accept-proxy to a bind configuration, it returns ssl handshake error. Without accept-proxy all is fine except I cannot get the original IP from the connecting client.

Let me introduce the arcitecture:

One frontend public server with HAProxy (Server A). This server is also a VPN server where the internal HAProxy server connects over VPN so Server A and Server B shares a dedicated network.

```auto
global
	log /dev/log local0
	log /dev/log local1 notice
	chroot /var/lib/haproxy
	stats socket /run/haproxy/admin.sock mode 660 level admin expose-fd listeners
	stats timeout 30s
	user haproxy
	group haproxy
	daemon

	# Default SSL material locations
	#ca-base /etc/ssl/certs
	#crt-base /etc/ssl/private

	# See: https://ssl-config.mozilla.org/#server=haproxy&server-version=2.0.3&config=intermediate
	#ssl-default-bind-ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA3> #ssl-default-bind-ciphersuites TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256
	#ssl-default-bind-options ssl-min-ver TLSv1.2 no-tls-tickets
		
defaults
	log global
	mode http
	option httplog
	option dontlognull
	timeout connect 5000
	timeout client 50000
	timeout server 50000
	errorfile 400 /etc/haproxy/errors/400.http
	errorfile 403 /etc/haproxy/errors/403.http
	errorfile 408 /etc/haproxy/errors/408.http
	errorfile 500 /etc/haproxy/errors/500.http
	errorfile 502 /etc/haproxy/errors/502.http
	errorfile 503 /etc/haproxy/errors/503.http
	errorfile 504 /etc/haproxy/errors/504.http

frontend http-in
  bind *:80
  mode http
  option forwardfor
  # Define hosts
  use_backend nc-http-bk if { hdr(host) -i cloud.mydomain.tld }
  redirect scheme https code 301 if { hdr(Host) -i www.mydomain.tld } !{ ssl_fc }

backend nc-http-bk
  balance roundrobin
  mode http
  option forwardfor
  #source 0.0.0.0 usesrc clientip
  server node1 xxx.xxx.xxx.xxx:80 check send-proxy

frontend env_ssl_frontend
  bind *:443
  mode tcp
  http-request redirect scheme https if ! { ssl_fc }
  option tcplog
  option tcp-check
  tcp-request inspect-delay 10s
  tcp-request content accept if { req_ssl_hello_type 1 }
  use_backend bk-https-nc if { req_ssl_sni -i cloud.mydomain.tld }
  use_backend bk-https-www if { req_ssl_sni -i www.mydomain.tld }
  
backend bk-https-nc
  balance roundrobin
  mode tcp
  #source 0.0.0.0 usesrc clientip
  option ssl-hello-chk
  server main xxx.xxx.xxx.xxx:443 check send-proxy
  #check fall 3 rise 2 send-proxy

backend bk-https-www
  balance roundrobin
  mode tcp
  #source 0.0.0.0 usesrc clientip
  option ssl-hello-chk
  server main xxx.xxx.xxx.xxx:443 check send-proxy

```

Server B is internal and is used by all devices and clients on the internal network.

```auto
global
  log /dev/log local0
  log /dev/log local1 notice
  stats socket /haproxy-admin.sock mode 660 level admin
  stats timeout 30s
  daemon
  #ssl-default-bind-options ssl-min-ver TLSv1.2 prefer-server-ciphers
  #ssl-default-bind-ciphers ECDH+AESGCM:ECDH+CHACHA20:ECDH+AES256:ECDH+AES128:!aNULL:!SHA1:!AESCCM
  #ssl-default-server-options ssl-min-ver TLSv1.3
  #ssl-default-server-ciphers ECDH+AESGCM:ECDH+CHACHA20:ECDH+AES256:ECDH+AES128:!aNULL:!SHA1:!AESCCM

defaults
  maxconn 1000
  mode http
  log global
  option http-server-close
  option dontlognull # bind *:443 ssl crt .
  timeout http-request 5s
  timeout connect 30s
  timeout client 4h # ddos protection
  timeout server 4h # stick-table type ip size 100k expire 30s store conn_cur
  #option forwardfor

frontend http-in
  bind *:80
  mode http
  option forwardfor
  # Define hosts
  use_backend nc-http-bk if { hdr(host) -i cloud.mydomain.tld }
  redirect scheme https code 301 if { hdr(Host) -i www.mydomain.tld } !{ ssl_fc }
  
# Internal trafic  
frontend env_ssl_frontend
  bind xxx.xxx.xxx.xxx:443
  mode tcp
  http-request redirect scheme https if ! { ssl_fc }
  option tcplog
  option tcp-check
  tcp-request inspect-delay 10s
  tcp-request content accept if { req_ssl_hello_type 1 }
  use_backend bk-https-nc if { req_ssl_sni -i cloud.mydomain.tld }
  use_backend bk-https-www if { req_ssl_sni -i www.mydomain.tld }

# From VPN tunnel (public)
frontend env_vpn_ssl
  bind xxx.xxx.yyy.xxx:443
  mode tcp
  http-request redirect scheme https if ! { ssl_fc }
  option tcplog
  tcp-request inspect-delay 10s
  tcp-request content accept if { req_ssl_hello_type 1 }
  use_backend bk-https-nc if { req_ssl_sni -i cloud.mydomain.tld }
  use_backend bk-https-www if { req_ssl_sni -i www.mydomain.tld }
  
backend nc-http-bk
  balance roundrobin
  mode http
  option forwardfor
  #source 0.0.0.0 usesrc clientip
  server node1 xxx.xxx.xxx.xxx:8080 check send-proxy

backend bk-https-nc
  balance roundrobin
  mode tcp
  #source 0.0.0.0 usesrc clientip
  option ssl-hello-chk
  server main xxx.xxx.xxx.xxx:4443 send-proxy
  #check fall 3 rise 2 send-proxy

backend bk-https-www
  balance roundrobin
  mode tcp
  #source 0.0.0.0 usesrc clientip
  option ssl-hello-chk
  server main xxx.xxx.xxx.xxx:4443 send-proxy
  #check fall 3 rise 2 send-proxy

```

If I adds

```auto
frontend env_vpn_ssl
  bind xxx.xxx.yyy.xxx:443 accept-proxy

```

Then I get an SSL Handshake error on my downstream endpoint. Without that one, all trafic is proxied without any other error, but the connecting IP in the webserver behind Server B, is recognised to be the VPN tunnel IP of Server A.

I have tested using send-proxy-v2 but same result. Any ideas?

---

<div class="post-metadata">

**Author:** ![lukastribus](https://avatars.discourse-cdn.com/v4/letter/l/7ea924/32.png) [@lukastribus](https://discourse.haproxy.org/u/lukastribus)\
**Post date:** [August 2, 2021, 2:18pm UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/2 "2021-08-02T14:18:56Z")

</div>

When you set `accept-proxy`, the client needs to send to actually send the PROXY protocol. If it doesn’t, it will not work.

So `accept-proxy` belongs on a bind line that recieves traffic from another haproxy instance configured on the backend with `send-proxy`.

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 8:21am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/3 "2021-08-03T08:21:35Z")

</div>

Thats what I do.

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 8:23am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/4 "2021-08-03T08:23:44Z")

</div>

Server A:  
Public server with public IP, receives the trafic from outside.

Server B:  
Internal “backend” HAProxy server.

Server A proxies port 80 and 443 from public IP to internal HAProxy (Server B) through a VPN network.

---

<div class="post-metadata">

**Author:** ![lukastribus](https://avatars.discourse-cdn.com/v4/letter/l/7ea924/32.png) [@lukastribus](https://discourse.haproxy.org/u/lukastribus)\
**Post date:** [August 3, 2021, 8:50am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/5 "2021-08-03T08:50:49Z")

</div>

Remove **[option ssl-hello-chk](http://cbonte.github.io/haproxy-dconv/2.4/configuration.html#4.2-option%20ssl-hello-chk)** everywhere, this will break when the proxy protocol is used, because it is a statically constructed SSLv3 `client_hello`. Instead you should use the SSL layer to health check, if that’s what you need (using [check-ssl](http://cbonte.github.io/haproxy-dconv/2.4/configuration.html#check-ssl))…

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 8:52am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/6 "2021-08-03T08:52:09Z")

</div>

Ah! Makes sense! Thanks.

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 9:27am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/7 "2021-08-03T09:27:13Z")

</div>

I have removed all ssl-hello-chk but I have same error.

---

<div class="post-metadata">

**Author:** ![lukastribus](https://avatars.discourse-cdn.com/v4/letter/l/7ea924/32.png) [@lukastribus](https://discourse.haproxy.org/u/lukastribus)\
**Post date:** [August 3, 2021, 9:50am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/8 "2021-08-03T09:50:30Z")

</div>

First of all disable health checks by removing the check keyword on the server line. At least we will know whether this is about failing health checks or other issues.

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 9:51am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/9 "2021-08-03T09:51:31Z")

</div>

Everywhere or just for the frontends and backends in scope?

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 9:55am UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/10 "2021-08-03T09:55:52Z")

</div>

All checks removed. Same error.

---

<div class="post-metadata">

**Author:** ![lukastribus](https://avatars.discourse-cdn.com/v4/letter/l/7ea924/32.png) [@lukastribus](https://discourse.haproxy.org/u/lukastribus)\
**Post date:** [August 3, 2021, 12:35pm UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/11 "2021-08-03T12:35:10Z")

</div>

Can you try temporarily using a default\_backend in frontend env\_vpn\_ssl, to see if SNI matches stop working in this case and if that is the only issue here?

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 12:43pm UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/12 "2021-08-03T12:43:20Z")

</div>

Sure.

---

<div class="post-metadata">

**Author:** ![Kerasit](https://avatars.discourse-cdn.com/v4/letter/k/7ab992/32.png) [@Kerasit](https://discourse.haproxy.org/u/Kerasit)\
**Post date:** [August 3, 2021, 12:49pm UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/13 "2021-08-03T12:49:14Z")

</div>

Nope. Using default\_backend on Server A and Server B, same error.  
Really appreciates the help!

---

<div class="post-metadata">

**Author:** ![lukastribus](https://avatars.discourse-cdn.com/v4/letter/l/7ea924/32.png) [@lukastribus](https://discourse.haproxy.org/u/lukastribus)\
**Post date:** [August 3, 2021, 12:52pm UTC](https://discourse.haproxy.org/t/accept-proxy-stops-working/6774/14 "2021-08-03T12:52:29Z")

</div>

In this case we need:

- full logging in `option tcplog` mode from both haproxy instances
- traffic capture between the two haproxy instances, between the client and instance a and between instance b and the server
