discourse/dockerでNginxの設定を直接変更するには?

Discourse インストールが HAProxy の背後にあるため、Nginx/Docker の設定を変更したいと考えています。現在、以下の問題に直面しています:

Discourse インストールに接続するすべての IP アドレスが、HAProxy の IP アドレスとして表示されます。

Nginx の設定ファイルに以下の行を追加する必要があります:

set_real_ip_from 127.0.0.1;
real_ip_header proxy_protocol;

これにより、Discourse インストールに接続する公開 IP アドレスを Nginx に渡すことができます。
ご協力ありがとうございます。

おそらく、以下のみを設定するべきではありません

set_real_ip_from 127.0.0.1;
real_ip_header proxy_protocol;

これは、以下の両方が真の場合にのみ正しいです:

  1. HAProxy が実際に PROXY プロトコルを Discourse コンテナに送信している。
  2. Discourse コンテナ内の Nginx が HAProxy を 127.0.0.1 として認識している。

多くの HAProxy → Discourse Docker 環境では、PROXY プロトコルではなく X-Forwarded-For を使用する方が、シンプルで一般的なアプローチです。

HAProxy 側では、転送先 IP ヘッダーを送信するように設定してください:

defaults
    mode http
    option httplog
    option forwardfor

または、バックエンド側で以下のように設定します:

backend be_discourse
    option forwardfor
    server app 127.0.0.1:8080 check

その後、Discourse コンテナの設定において、app.yml を通じて Nginx の実 IP 設定の変更を永続化してください。実行中のコンテナ内部でファイルを直接編集しないでください。再構築時にそれらの変更は失われるためです。

/var/discourse/containers/app.yml の既存の run: セクションに、以下のような内容を追加します:

run:
  - replace:
      filename: /etc/nginx/conf.d/discourse.conf
      from: "types {"
      to: |
        set_real_ip_from 127.0.0.1;
        # HAProxy が接続する実際の Docker ブリッジ/ネットワーク範囲に合わせて調整してください
        set_real_ip_from 172.17.0.0/16;
        real_ip_header X-Forwarded-For;
        real_ip_recursive on;
        types {

その後、再構築を実行します:

cd /var/discourse
./launcher rebuild app

HAProxy が Discourse コンテナ内の Nginx に接続する際に、Nginx が実際に認識する送信元 IP/範囲に合わせて、set_real_ip_from の値を調整する必要がある場合があります。Docker を使用している場合、これは 127.0.0.1 ではなく、172.17.0.1 のような Docker ブリッジアドレスや、ユーザー定義の Docker ネットワーク範囲であることがよくあります。

PROXY プロトコルを使用したい場合は、HAProxy が明示的にそれを送信する必要があります:

backend be_discourse
    server app 127.0.0.1:8080 check send-proxy

また、Nginx は単に real_ip_header proxy_protocol を読み取るだけでなく、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 {

重要な修正点は、real_ip_header proxy_protocol だけでは不十分ということです。Nginx には listen 80 proxy_protocol; も必要であり、HAProxy には send-proxy が必要です。それ以外の場合は、HAProxy の HTTP モード設定で標準的に使用される X-Forwarded-For を使用してください。HAProxy では、option forwardforX-Forwarded-For クライアント IP ヘッダーを追加する標準的な方法です。Nginx の PROXY プロトコルを使用する場合、real_ip_header proxy_protocol が機能するためには、listen ディレクティブに proxy_protocol が含まれている必要があります。

つまり、簡潔に言うと:

  • PROXY プロトコルを使用する特別な理由がない限り、X-Forwarded-For を使用してください。
  • 両方のモードを混在させないでください。
  • HAProxy が send-proxy を使用していない場合、real_ip_header proxy_protocol は機能しません。
  • Discourse Docker を使用している場合、実行中のコンテナ内部ではなく、app.yml で変更を行ってください。