Docker で環境構築した Nginxの設定(nginx.conf)をカスタマイズする方法

NginxCustom

こんにちはフロントエンドエンジニアのまさにょんです!

今回は、Docker で環境構築した Nginxの設定(nginx.conf)をカスタマイズする方法について解説していきます。

Docker で Nginxの環境を構築する方法は、以前に記事にしていますので、そちらをご確認ください。

Docker で環境構築した Nginxの設定をカスタマイズする方法

実務で、Docker 上で展開している Nginxの設定をカスタマイズする必要がでてきたので、その調査 & 対応結果の記事になります。

まず Nginxの設定をカスタマイズする方法の結論を言うと、Local プロジェクト内にカスタマイズした nginx.confを用意して、

Dockerfileordocker-compose.ymlを使って、それを Docker Container内の/etc/nginx/nginx.conf に Copyすることで、カスタマイズを反映することができます。

Nginxの設定をカスタマイズする要件の定義

今回、Nginxの設定をカスタマイズしたい内容 (要件の定義) は、次のとおりです。

  1. Response Header にサーバー情報が出力されている問題を解決したい。
  2. X-Frame-Optionsヘッダが、Set されていない問題を解決したい。

解決方法など詳細は、それぞれ後述します。

Response Header にサーバー・バージョン情報が出力されている問題を解決する

Nginx の Default設定では、Response Header にサーバーのバージョン情報が出力されてしまいます。

例えば、curl http://localhost:80/ -I "accept: application/json" で Sever からの Response Header を確認すると、

Server: nginx/1.19.10 とバージョン情報が出力されてしまっていることがわかります。

わざわざ、WebServerのバージョン情報を表示してしまうと、セキュリティ上のリスクになる可能性もあるとのことで、これを表示しないように設定していきます。

Nginx_Test % curl http://localhost:80/ -I "accept: application/json"

# [ 出力結果 ]
HTTP/1.1 200 OK
Server: nginx/1.19.10
Date: Sat, 08 Jul 2023 04:02:23 GMT
Content-Type: text/html
Content-Length: 106
Last-Modified: Sat, 08 Jul 2023 03:19:42 GMT
Connection: keep-alive
ETag: "64a8d5ce-6a"
Accept-Ranges: bytes

今回は、Dockerで Nginx の環境構築をする方法と基本設定について(ハンズオン) で作成した、

docker-compose.ymlvolumes./nginx.conf:/etc/nginx/nginx.conf を追加します。

version: "3.8"
services:
  # Nginx (Web-Server)
  nginx:
    container_name: "nginx"
    image: nginx:1.19
    ports:
      - "80:80"
    volumes:
      - ./html:/usr/share/nginx/html
      - ./nginx.conf:/etc/nginx/nginx.conf

続いて、プロジェクト内にカスタマイズするためのnginx.conf を作成します。

# worker プロセスのユーザ名
user  nginx;
# worker プロセスの数
worker_processes  1;
# プロセス数はデフォルトで1となっていますが worker_processes auto; とすることで、CPUコア数と同数のプロセスを選択することができます。

# エラーログの出力先とログレベルの設定です。
error_log  /var/log/nginx/error.log warn;
# ログレベルには debug, info, notice, warn, error, crit, alert, emerg が設定可能です。

# プロセスIDの記載先となるPIDファイルの格納先の指定です。
pid        /var/run/nginx.pid;


# モジュール名 { } という形で、それぞれのモジュールに対する設定を行います。
# 指定したモジュールのスコープは { } で囲まれた範囲となり、これをコンテキストと呼びます。
events {
    # worker_connections で、イベントループを行う worker プロセスで同時に受付可能な接続数を定義しています。
    worker_connections  1024;
}

http {
    # 追加設定-1. server_tokens off; => Nginxのサーバー情報をResponseヘッダーから除外する
    server_tokens off;
    include       /etc/nginx/mime.types;
    default_type  application/octet-stream;

    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

    access_log  /var/log/nginx/access.log  main;

    sendfile        on;
    #tcp_nopush     on;

    keepalive_timeout  65;

    #gzip  on;

    include /etc/nginx/conf.d/*.conf;
}

コメントがいろいろありますが、Response Header にサーバー情報が出力されている問題を解決するために追加したのは、次の内容になります。

# 追加設定-1. server_tokens off; => Nginxのサーバー情報をResponseヘッダーから除外する
server_tokens off;

X-Frame-Optionsヘッダが、Set されていない問題を解決する

続いて、X-Frame-Optionsヘッダが、Set されていない問題を解決していきます。

ちなみに、X-Frame-Optionsヘッダが、Set されていないと、クリックジャッキング というセキュリティリスクがあるため、これも対応すべき問題になります。

こちらもnginx.confに次のような設定を追加していきます。

# 追加設定-2. X-Frame-Options(クリックジャッキング対策(add_header))
add_header X-Frame-Options SAMEORIGIN;

add_header X-Frame-Options SAMEORIGIN; を追加すると、nginx.confは次のような内容になりました。

# worker プロセスのユーザ名
user  nginx;
# worker プロセスの数
worker_processes  1;
# プロセス数はデフォルトで1となっていますが worker_processes auto; とすることで、CPUコア数と同数のプロセスを選択することができます。

# エラーログの出力先とログレベルの設定です。
error_log  /var/log/nginx/error.log warn;
# ログレベルには debug, info, notice, warn, error, crit, alert, emerg が設定可能です。

# プロセスIDの記載先となるPIDファイルの格納先の指定です。
pid        /var/run/nginx.pid;


# モジュール名 { } という形で、それぞれのモジュールに対する設定を行います。
# 指定したモジュールのスコープは { } で囲まれた範囲となり、これをコンテキストと呼びます。
events {
    # worker_connections で、イベントループを行う worker プロセスで同時に受付可能な接続数を定義しています。
    worker_connections  1024;
}

http {
    # 追加設定-1. server_tokens off; => Nginxのサーバー情報をResponseヘッダーから除外する
    server_tokens off;
    include       /etc/nginx/mime.types;
    default_type  application/octet-stream;

    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

    access_log  /var/log/nginx/access.log  main;

    sendfile        on;
    #tcp_nopush     on;

    keepalive_timeout  65;

    # 追加設定-2. X-Frame-Options(クリックジャッキング対策(add_header))
    add_header X-Frame-Options SAMEORIGIN;

    #gzip  on;

    include /etc/nginx/conf.d/*.conf;
}

Nginxの設定をカスタマイズ後の動作確認・Test

それでは、実際に上記の 2つの追加設定が、Nginxに反映されているかの動作確認・Testを実施します。

まずは、Nginx の Docker Container を Stopします。

docker compose down

Nginx の Docker Container を立ち上げて、nginx.confを読み込ませます。

docker-compose up -d

続いて、curl http://localhost:80/ -I "accept: application/json"を実行すると、

Server のバージョン情報が表示されず、X-Frame-Options: SAMEORIGIN が Setされていることが確認できます。

Nginx_Test % curl http://localhost:80/ -I "accept: application/json"

# [ 出力結果 ]
HTTP/1.1 200 OK
Server: nginx
Date: Sun, 09 Jul 2023 08:59:30 GMT
Content-Type: text/html
Content-Length: 106
Last-Modified: Sat, 08 Jul 2023 03:19:42 GMT
Connection: keep-alive
ETag: "64a8d5ce-6a"
X-Frame-Options: SAMEORIGIN
Accept-Ranges: bytes

ちなみに、今回のように Request Headerを確認したいときは、

curl http://localhost:80/ -I "accept: application/json" コマンドを実行する方法と、

Webブラウザの DevToolsのNetwork確認機能で、確認することができます。

Dockerの学習・参考書

参考・引用

  1. Docker による nginx の導入と基本設定
  2. Nginxセキュリティ設定
  3. クリックジャッキングとその対策について調べた件
  4. nginxについてまとめ(設定編)

最近の投稿