Gerenciando a "cadeia de confiança" do IP real do usuário final

Contexto

O Discourse precisa ter conhecimento do endereço IP real do usuário final.

No entanto, um usuário final nunca se conecta diretamente ao Discourse, pois sempre há um ou mais servidores web upstream (nginx rodando no container do Discourse) em funcionamento. Assim, precisamos de uma maneira de passar essas informações para o Discourse de forma confiável.

O cabeçalho x-forwarded-for é a solução. Neste tópico, descreverei os mecanismos específicos para lidar adequadamente com essas informações e como esperamos que sejam propagadas.

Modelos

Os vários modelos para confiar em proxies upstream (por exemplo, cloudflare.template.yml ou fastly.template.yml) foram atualizados para usar nomes de arquivos previsíveis em outlets, em vez de depender de substituição de texto (que é frágil).

Nomes de arquivos

server/real-ip-header.conf

Este arquivo contém o cabeçalho que o nginx rodando no container usará como fonte de verdade, por exemplo:

real_ip_header x-forwarded-for;

ou conforme definido no modelo Cloudflare:

real_ip_header cf-connecting-ip;

server/real-ip-recursive.conf

Se este arquivo existir, ele controla a recursão no processamento do cabeçalho “IP real”. Você precisará habilitar isso se houver mais de um proxy na frente do container do Discourse.

real_ip_recursive on;

Exemplo:

Cloudflare → Balanceador de carga → Container do Discourse (que é nginx + Discourse em si)

Com essa configuração, o nginx receberá um x-forwarded-for que parece:

x-forwarded-for: ip_real_usuario_final, ip_cloudflare

em uma conexão de um IP de balanceador de carga.

Para processar isso, primeiro o nginx determina se o endereço de origem da conexão (o IP do balanceador de carga) é confiável (ver set_real_ip_from) e, se for, processará o último IP do cabeçalho x-forwarded-for.

Como esse endereço IP é ip_cloudflare, o nginx então precisa fazer isso novamente, verificando se ip_cloudflare é confiável e usando o próximo endereço IP, que é ip_real_usuario_final.

server/set-real-ip-from-ENVIRONMENT.conf

Este arquivo contém diretivas que dizem ao nginx quais endereços IP confiar, e podemos ter quantos arquivos e diretivas forem necessários.

Os modelos em discourse_docker criam esses arquivos conforme necessário (por exemplo, set-real-ip-from-cloudflare.conf) e, se você tiver necessidades adicionais, pode adicionar os seus próprios.

Exemplo:

Se você estiver executando no AWS e tiver um ALB na frente do container do Discourse, pode adicionar um arquivo adicional adicionando o seguinte à sua definição de container (adaptado ao seu ambiente):

run:
  - file:
      path: /etc/nginx/conf.d/outlets/server/set-real-ip-from-aws.conf
      chmod: 644
      # A VPC da AWS é 10.42.0.0/16, confie em qualquer conexão das redes do ALB
      contents: |
        set_real_ip_from 10.42.66.0/24;
        set_real_ip_from 10.42.67.0/24;
  - file:
      path: /etc/nginx/conf.d/outlets/server/real-ip-header.conf
      chmod: 644
      contents: |
        real_ip_header x-forwarded-for;
4 curtidas