Ensure that HAProxy keep up with Docker name resolution.
HAProxy works great as a docker container.
$ docker exec haproxy cat /usr/local/etc/haproxy/haproxy.cfg
global stats socket /var/run/api.sock user haproxy group haproxy mode 660 level admin expose-fd listeners log stdout format raw local0 info defaults mode http timeout client 25s timeout connect 5s timeout server 10000s timeout http-request 10s timeout tunnel 3600s timeout http-keep-alive 1s timeout http-request 15s timeout queue 30s timeout tarpit 60s log global frontend frontend_https mode http bind :80 bind *:443 ssl crt /certs/octocat.cloud.pem http-request redirect scheme https unless { ssl_fc } http-request set-header X-Forwarded-Proto https if { ssl_fc } option forwardfor acl is_draw hdr(host) -i draw.octocat.cloud use_backend draw_backend if is_draw backend draw_backend server draw draw:8080
There is a caveat though as by default backend will not update its servers when you alter these containers.
$ curl https://docs.octocat.cloud/
<html><body><h1>503 Service Unavailable</h1> No server is available to handle this request. </body></html>
The solution is to directly define docker resolver and use for every backend server.
$ docker exec haproxy cat /usr/local/etc/haproxy/haproxy.cfg
global stats socket /var/run/api.sock user haproxy group haproxy mode 660 level admin expose-fd listeners log stdout format raw local0 info defaults mode http timeout client 25s timeout connect 5s timeout server 10000s timeout http-request 10s timeout tunnel 3600s timeout http-keep-alive 1s timeout http-request 15s timeout queue 30s timeout tarpit 60s log global resolvers docker_resolver nameserver dns 127.0.0.11:53 frontend frontend_https mode http bind :80 bind *:443 ssl crt /certs/octocat.cloud.pem http-request redirect scheme https unless { ssl_fc } http-request set-header X-Forwarded-Proto https if { ssl_fc } option forwardfor acl is_draw hdr(host) -i draw.octocat.cloud use_backend draw_backend if is_draw backend draw_backend server draw draw:8080 resolvers docker_resolver resolve-prefer ipv4
This will ensure that backend server address will stay up to date whenever you update the target container.