Resolvendo o problema em que todos os usuários do Discourse implantado com o 1Panel exibem o IP vindo do Cloudflare em vez do IP real do navegador do usuário

Instalei o 1Panel no meu VPS, configurei o Discourse (implantação em contêiner) e utilizei o OpenResty (implantação em contêiner) como proxy reverso. O domínio está hospedado no Cloudflare com o CDN (nuvem amarela) ativado. Abaixo, apresento um tutorial para resolver o problema em que o IP do usuário aparece como sendo do Cloudflare, em vez do IP real do navegador do usuário.

1. Criar uma tarefa agendada no 1Panel para baixar semanalmente a lista atualizada de IPs do Cloudflare e salvá-la no diretório de configuração do OpenResty.

  1. No menu lateral esquerdo do 1Panel, clique em “Tarefas Agendadas”.

  2. No canto superior direito, clique em “Criar Tarefa Agendada”.

  3. Preencha os seguintes parâmetros (basta copiar e colar):

  • Tipo de tarefa: Selecione Script Shell.

  • Nome da tarefa: Por exemplo, Atualização Automática dos Intervalos de IP do Cloudflare.

  • Ciclo de execução: Recomenda-se Semanal (por exemplo, todos os sábados às 03:00 da manhã).

  • Conteúdo do script: Copie e cole o código completo abaixo (Nota: Antes de tudo, modifique o nome do contêiner e o caminho do diretório de configuração no topo do código):

#!/bin/bash
# Área de configuração
CONTAINER_NAME="Nome do contêiner do openresty no 1Panel"
# Altere para o diretório proxy do site especificado
CONF_DIR="/opt/1panel/www/sites/www.seudominio.com/proxy"

echo "[$(date)] Iniciando a busca dos intervalos de IP mais recentes no Cloudflare oficial..."
TEMP_DIR=$(mktemp -d)

# Buscar e converter a lista de IPs para o formato reconhecido pelo Nginx
curl -fsS https://www.cloudflare.com/ips-v4 | sed 's/.*/set_real_ip_from \0;/' > $TEMP_DIR/cf-ips-v4.conf
curl -fsS https://www.cloudflare.com/ips-v6 | sed 's/.*/set_real_ip_from \0;/' > $TEMP_DIR/cf-ips-v6.conf

# Verificar e mover os arquivos
if [[ -s $TEMP_DIR/cf-ips-v4.conf ]] && [[ -s $TEMP_DIR/cf-ips-v6.conf ]]; then
    mv $TEMP_DIR/cf-ips-v4.conf $CONF_DIR/
    mv $TEMP_DIR/cf-ips-v6.conf $CONF_DIR/
    echo "[$(date)] Arquivos de configuração atualizados com sucesso para $CONF_DIR."
else
    echo "[$(date)] Erro: Falha ao buscar os IPs do Cloudflare!"
    rm -rf $TEMP_DIR
    exit 1
fi
rm -rf $TEMP_DIR

# Testar e recarregar o Nginx
echo "[$(date)] Realizando teste de configuração do Nginx..."
if docker exec $CONTAINER_NAME nginx -t; then
    docker exec $CONTAINER_NAME nginx -s reload
    echo "[$(date)] Sucesso! Recarregamento da configuração do OpenResty concluído."
else
    echo "[$(date)] Falha! O teste de configuração do Nginx não foi aprovado."
    exit 1
fi

Após criar a tarefa, não é necessário esperar até sábado; você pode testar imediatamente: na lista de “Tarefas Agendadas”, localize a tarefa recém-criada.

Clique no botão “Relatório” à direita. Verifique a janela de logs que aparecer. Se as últimas linhas mostrarem Sucesso! Recarregamento da configuração do OpenResty concluído, significa que todo o processo foi executado com perfeição dentro do 1Panel!

2. Configuração adicional de realip no OpenResty

No diretório /opt/1panel/www/sites/www.seudominio.com/proxy/ da máquina hospedeira, crie um novo arquivo (o nome é livre, desde que termine em .conf, e será carregado automaticamente pela configuração principal via include *.conf): realip.conf

real_ip_header CF-Connecting-IP;
real_ip_recursive on;

3. Recarregar o OpenResty

docker exec NomeDoConteinerOpenRestyNo1Panel nginx -t
docker exec NomeDoConteinerOpenRestyNo1Panel nginx -s reload

4. Verificar se o OpenResty obteve o IP real

Verifique o access log do OpenResty:

tail -f /opt/1panel/www/sites/www.seudominio.com/log/access.log

Se a configuração estiver correta, o primeiro IP nos logs deve ser o seu IP público real, e não os intervalos do Cloudflare como 173.245.x.x.

5. Observações sobre o lado do Discourse

Adicionar - "templates/cloudflare.template.yml" no arquivo app.yml do Discourse só é eficaz quando o Discourse está diretamente exposto ao Cloudflare. Como há um proxy reverso OpenResty no meio, o contêiner do Discourse vê o IP de origem como o gateway do Docker (por exemplo, 172.17.0.1 ou 172.18.0.1), portanto, o set_real_ip_from <CloudflareIP> presente nesse modelo não será correspondido.

No entanto, desde que você restaure o IP real na camada do OpenResty seguindo os passos acima e transmita um cabeçalho X-Forwarded-For limpo, o Rails no backend do Discourse conseguirá identificar corretamente o IP real do usuário, pois o Rails já confia por padrão em intervalos de rede privados do Docker como 172.x.x.x.

Portanto, não é necessário adicionar - "templates/cloudflare.template.yml" no arquivo app.yml do Discourse.