Como posso modificar a configuração do Nginx diretamente dentro do discourse/docker?

Gostaria de modificar a configuração do Nginx/Docker, pois minha instalação do Discourse está atrás de um HAProxy. O problema que estou enfrentando é o seguinte:
Todos os endereços IP que se conectam à minha instalação do Discourse aparecem como o endereço IP do HAProxy.
Preciso adicionar as seguintes linhas ao arquivo de configuração do Nginx:

set_real_ip_from 127.0.0.1;
real_ip_header proxy_protocol;

…para que os endereços IP públicos que se conectam à minha instalação do Discourse sejam passados ao Nginx.
Obrigado pela ajuda.

Provavelmente você não quer apenas:

set_real_ip_from 127.0.0.1;
real_ip_header proxy_protocol;

Isso só está correto se ambas as condições abaixo forem verdadeiras:

  1. O HAProxy está realmente enviando o protocolo PROXY para o container do Discourse.
  2. O Nginx dentro do container do Discourse vê o HAProxy como 127.0.0.1.

Em muitas configurações de Docker com HAProxy → Discourse, a abordagem mais simples e comum é usar X-Forwarded-For, e não o protocolo PROXY.

Para o HAProxy, certifique-se de que ele envie o cabeçalho de IP encaminhado:

defaults
    mode http
    option httplog
    option forwardfor

ou no backend:

backend be_discourse
    option forwardfor
    server app 127.0.0.1:8080 check

Em seguida, na configuração do container do Discourse, persista as alterações de IP real do Nginx por meio do app.yml. Não edite os arquivos diretamente dentro do container em execução, pois eles serão perdidos na reconstrução.

Adicione algo como isso ao /var/discourse/containers/app.yml na seção run: existente:

run:
  - replace:
      filename: /etc/nginx/conf.d/discourse.conf
      from: "types {"
      to: |
        set_real_ip_from 127.0.0.1;
        # ajuste isso para a faixa de rede/ponte Docker real da qual o HAProxy se conecta
        set_real_ip_from 172.17.0.0/16;
        real_ip_header X-Forwarded-For;
        real_ip_recursive on;
        types {

Em seguida, reconstrua:

cd /var/discourse
./launcher rebuild app

Pode ser necessário ajustar set_real_ip_from para corresponder ao IP/faixa de origem real que o Nginx dentro do container do Discourse vê quando o HAProxy se conecta a ele. Com Docker, isso geralmente não é 127.0.0.1; pode ser um endereço de ponte Docker, como 172.17.0.1, ou uma faixa de rede Docker definida pelo usuário.

Se você realmente quiser usar o protocolo PROXY, o HAProxy deve enviá-lo explicitamente:

backend be_discourse
    server app 127.0.0.1:8080 check send-proxy

e o Nginx deve ouvir com proxy_protocol, não apenas ler real_ip_header proxy_protocol:

run:
  - replace:
      filename: /etc/nginx/conf.d/discourse.conf
      from: "listen 80;"
      to: "listen 80 proxy_protocol;"

  - replace:
      filename: /etc/nginx/conf.d/discourse.conf
      from: "types {"
      to: |
        set_real_ip_from 127.0.0.1;
        set_real_ip_from 172.17.0.0/16;
        real_ip_header proxy_protocol;
        types {

A correção importante é: real_ip_header proxy_protocol sozinho é incompleto. O Nginx também precisa de listen 80 proxy_protocol;, e o HAProxy precisa de send-proxy. Caso contrário, use X-Forwarded-For, que é a configuração padrão do modo HTTP do HAProxy. No HAProxy, option forwardfor é a maneira padrão de adicionar o cabeçalho de IP do cliente X-Forwarded-For. Com o protocolo PROXY do Nginx, a diretiva listen deve incluir proxy_protocol antes que real_ip_header proxy_protocol possa funcionar.

Então, a versão resumida é:

  • Use X-Forwarded-For, a menos que você tenha um motivo específico para usar o protocolo PROXY.
  • Não misture os dois modos.
  • Se o HAProxy não estiver usando send-proxy, então real_ip_header proxy_protocol não funcionará.
  • Se estiver usando o Discourse Docker, faça a alteração no app.yml, e não diretamente dentro do container em execução.