I’m trying to configure a vanilla proxy which basically passed through a HTTPS connection to the server using HTTP CONNECT.
My haproxy config is as follows:
frontend main-http
bind *:80
mode http
option http-server-close
option forwardfor
acl url_whitelist url_dom -f /etc/haproxy/URL_Whitelist.txt
http-request deny if !url_whitelist
default_backend app-main-http
frontend main-https
bind *:443
mode tcp
tcp-request inspect-delay 5s
tcp-request content accept if { req_ssl_hello_type 1 }
default_backend app-main-https
backend app-main-http
mode http
backend app-main-https
mode tcp
The proxy works perfectly for HTTP. However, for HTTPS requests it gives me the “curl: (56) Proxy CONNECT aborted” when using CURL to test.
Does anyone know what I’m missing?
Thanks!
You are passing through the TCP payload on port 443, haproxy has nothing to do with the CONNECT request, it doesn’t even see it (as it is encrypted).
So in the HTTPS configuration, are relying on your backend to decrypt the TLS session and understand CONNECT request.
Can you share the complete backend configuration?
Unfortunately, that’s all my backend has and I guess that’s where I’m going wrong. How do I decrypt the TLS session and understand the CONNECT for SSL pass through?
My use case is to forward or deny the https request based on the destination. I’m looking to use fetchs like “hrd(host)” and “req.ssl_sni” to do the filtering.
Ex: https://www.wikipedia.org should work but https://www.google.com should not.
Is that possible?
Thanks!
Are you using haproxy as a forward proxy? Please explain your use case completely.
Okay. I want the HAProxy to be the entry point for HTTP and HTTPS requests from my client application. The client sends requests to a number of my own web servers as well as the open internet. I need to be able to deny requests to certain endpoints as well. In case of HTTP I’m doing that using an acl rule to deny http request if url_dom matches my blacklist of endpoints. I essentially need a similar implementation for HTTPS requests without having to terminate SSL at the proxy.
You cannot access high level information in HTTP while maintaining end-to-end encryption between the client and the destination server, that is exactly what SSL prevents in the first place.
You only choice is to decrypt SSL at the haproxy. Check the generate-certificates [1] directive, which allows certificates to be generated on the fly (but you have to deploy the CA root cert to the client first).
[1] https://cbonte.github.io/haproxy-dconv/1.7/configuration.html#5.1-generate-certificates
Okay, thanks for that!
Also, is it possible to fetch “dst” and filter based on client’s destination IP? for HTTP and HTTPS.
I tried to implement that in the tcp mode but was not successful.
The destination IP from the socket is the IP of haproxy itself, unless you are using transparent mode and haproxy is the default-gateway of your devices.
I think you need to go back to the drawing board and come up with a solution involving an actual forward proxy, like squid.
Yes, I will do that! Thanks for all the help!
Hello,
Are there example configurations I can look at to use HAProxy in the transparent mode? Any help is very much appreciated!
Thanks,
Juliet
The transparent mode is for the reverse proxy case, not the forward proxy case - it spoofs the client IP, it doesn’t connect to the original destination IP.
See:
You really need a forward proxy.