Skip to content
Published on

Nginx完全ガイド2025:リバースプロキシ、ロードバランシング、SSL、キャッシング、セキュリティまで

Authors

TOC

1. Nginxとは

Nginx(エンジンエックス)は、2004年にIgor SysoevがC10K問題(もんだい)を解決(かいけつ)するために開発(かいはつ)した高性能(こうせいのう)ウェブサーバーです。現在(げんざい)、世界(せかい)のウェブサーバー市場(しじょう)シェア1位(い)を占(し)めており、単純(たんじゅん)なウェブサーバーを超(こ)えてリバースプロキシ、ロードバランサー、HTTPキャッシュ、APIゲートウェイなど多様(たよう)な役割(やくわり)を果(は)たしています。

1.1 Nginx vs Apache

項目(こうもく)NginxApache
アーキテクチャイベント駆動(非同期(ひどうき))プロセス/スレッドベース
同時接続(どうじせつぞく)数万〜数十万数千(MPM設定(せってい)次第(しだい))
メモリ使用量接続(せつぞく)あたり数KB接続あたり数MB
静的(せいてき)ファイル非常に高速(こうそく)高速
動的(どうてき)コンテンツプロキシ(FastCGI/uWSGI)モジュール内蔵(ないぞう)(mod_php)
設定方式中央(ちゅうおう)集中型(しゅうちゅうがた).htaccess分散(ぶんさん)可能
ロードバランシング内蔵別途(べっと)モジュール必要
市場シェア約34%(1位)約29%(2位)

1.2 イベント駆動アーキテクチャ

Apache(プロセスモデル):
┌────────────┐
Master├────────────┤
Worker 1   │ → Client A(接続ごとに1プロセス)
Worker 2   │ → Client B
Worker 3   │ → Client C
...Worker 1000│ → Client 1000
└────────────┘
1000接続 = 1000プロセス/スレッド = 高メモリ使用

Nginx(イベントモデル):
┌────────────┐
Master├────────────┤
Worker 1   │ → epoll/kqueueで数千接続を処理
Worker 2   │ →(non-blocking I/OWorker 3   │ →
Worker 4   │ →(CPUコア数分だけ)
└────────────┘
10000接続 = 4 workers = 非常に低いメモリ使用

核心(かくしん)原理(げんり):

  • Masterプロセス: 設定読(よ)み込み、ワーカー管理(かんり)、ログ管理
  • Workerプロセス: 実際(じっさい)のリクエスト処理(しょり)(CPUコア数だけ生成(せいせい))
  • epoll/kqueue: OSレベルのイベント通知(つうち)メカニズム
  • Non-blocking I/O: リクエストを待(ま)たずに他(ほか)のリクエストを処理

1.3 インストール

# Ubuntu/Debian
sudo apt update
sudo apt install nginx

# CentOS/RHEL
sudo yum install epel-release
sudo yum install nginx

# macOS
brew install nginx

# Docker
docker run -d -p 80:80 -p 443:443 \
  -v /path/to/nginx.conf:/etc/nginx/nginx.conf:ro \
  -v /path/to/certs:/etc/nginx/certs:ro \
  --name nginx nginx:alpine

# 状態確認
sudo systemctl status nginx
nginx -t  # 設定文法チェック
nginx -V  # コンパイルオプション確認

2. 設定(せってい)構造(こうぞう)

2.1 設定ファイルレイアウト

/etc/nginx/
├── nginx.conf              # メイン設定
├── conf.d/                 # 追加設定(*.conf自動ロード)
│   ├── default.conf
│   └── myapp.conf
├── sites-available/        # 利用可能なサイト(Debian系)
│   └── mysite.conf
├── sites-enabled/          # 有効化されたサイト(シンボリックリンク)
│   └── mysite.conf -> ../sites-available/mysite.conf
├── mime.types              # MIMEタイプマッピング
├── fastcgi_params          # FastCGIパラメータ
└── snippets/               # 再利用可能な設定フラグメント
    ├── ssl-params.conf
    └── proxy-params.conf

2.2 設定ブロック階層(かいそう)

# /etc/nginx/nginx.conf

# グローバルコンテキスト
user nginx;
worker_processes auto;          # CPUコア数に自動設定
worker_rlimit_nofile 65535;     # ワーカーあたり最大ファイルディスクリプタ
error_log /var/log/nginx/error.log warn;
pid /run/nginx.pid;

# イベントコンテキスト
events {
    worker_connections 10240;   # ワーカーあたり最大同時接続数
    multi_accept on;            # 一度に複数接続を受け入れ
    use epoll;                  # Linux: epoll, BSD: kqueue
}

# HTTPコンテキスト
http {
    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" '
                    '$request_time $upstream_response_time';

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

    # パフォーマンス設定
    sendfile on;
    tcp_nopush on;
    tcp_nodelay on;
    keepalive_timeout 65;
    types_hash_max_size 2048;
    client_max_body_size 50m;

    # Gzip圧縮
    gzip on;
    gzip_vary on;
    gzip_min_length 1024;
    gzip_comp_level 5;
    gzip_types text/plain text/css application/json
               application/javascript text/xml application/xml
               application/xml+rss text/javascript image/svg+xml;

    # サーバーブロック読み込み
    include /etc/nginx/conf.d/*.conf;
}

2.3 ServerブロックとLocationブロック

server {
    listen 80;
    listen [::]:80;
    server_name example.com www.example.com;

    # 301リダイレクト(HTTP → HTTPS)
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name example.com www.example.com;

    # SSL設定
    ssl_certificate /etc/nginx/certs/fullchain.pem;
    ssl_certificate_key /etc/nginx/certs/privkey.pem;

    # ルートディレクトリ
    root /var/www/html;
    index index.html index.htm;

    # Location優先順位(高い順)
    # 1. 完全一致(=)
    location = /favicon.ico {
        log_not_found off;
        access_log off;
    }

    # 2. 優先プレフィックス(^~)
    location ^~ /static/ {
        alias /var/www/static/;
        expires 30d;
        add_header Cache-Control "public, immutable";
    }

    # 3. 正規表現(~, ~*)- 大文字小文字区別/無視
    location ~* \.(jpg|jpeg|png|gif|ico|css|js|woff2)$ {
        expires 7d;
        add_header Cache-Control "public";
    }

    # 4. プレフィックスマッチ(なしまたは/)
    location / {
        try_files $uri $uri/ /index.html;
    }

    # APIプロキシ
    location /api/ {
        proxy_pass http://backend;
        include snippets/proxy-params.conf;
    }

    # エラーページ
    error_page 404 /404.html;
    error_page 500 502 503 504 /50x.html;
    location = /50x.html {
        root /usr/share/nginx/html;
    }
}

2.4 Locationマッチング優先(ゆうせん)順位(じゅんい)

優先順位(高い順):
1. = (完全一致)              location = /path
2. ^~ (優先プレフィックス)    location ^~ /path
3. ~ (正規表現、大文字小文字区別) location ~ \.php$
4. ~* (正規表現、大文字小文字無視) location ~* \.(jpg|png)$
5. /path (プレフィックスマッチ) location /path
6. / (デフォルト)             location /

3. リバースプロキシ設定

3.1 基本(きほん)リバースプロキシ

# snippets/proxy-params.conf
proxy_http_version 1.1;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Connection "";

proxy_connect_timeout 60s;
proxy_send_timeout 60s;
proxy_read_timeout 60s;

proxy_buffering on;
proxy_buffer_size 4k;
proxy_buffers 8 4k;
proxy_busy_buffers_size 8k;
server {
    listen 443 ssl http2;
    server_name api.example.com;

    ssl_certificate /etc/nginx/certs/fullchain.pem;
    ssl_certificate_key /etc/nginx/certs/privkey.pem;

    location / {
        proxy_pass http://127.0.0.1:3000;
        include snippets/proxy-params.conf;
    }
}

3.2 リバースプロキシの動作(どうさ)原理(げんり)

Client                    Nginx (Reverse Proxy)              Backend
  │                              │                              │
GET /api/users              │                              │
  │─────────────────────────────>│                              │
  │                              │  GET /api/users              │
  │                              │  Host: api.example.com  │                              │  X-Real-IP: 203.0.113.1  │                              │  X-Forwarded-For: 203.0.113.1  │                              │─────────────────────────────>  │                              │                              │
  │                              │  200 OK  │                              │<─────────────────────────────│
200 OK                      │                              │
<─────────────────────────────│                              │

3.3 パスリライト

# /api/v1/users → バックエンドの/usersに転送
location /api/v1/ {
    rewrite ^/api/v1/(.*)$ /$1 break;
    proxy_pass http://backend;
    include snippets/proxy-params.conf;
}

# またはproxy_passにURI含める
location /api/v1/ {
    proxy_pass http://backend/;  # 末尾のスラッシュに注意!
    include snippets/proxy-params.conf;
}

# 条件付きリダイレクト
location /old-page {
    return 301 /new-page;
}

4. ロードバランシング

4.1 Upstream設定

# デフォルト Round Robin
upstream backend {
    server 10.0.0.1:8080;
    server 10.0.0.2:8080;
    server 10.0.0.3:8080;
}

# Least Connections - アクティブ接続が最も少ないサーバーへ
upstream backend_least {
    least_conn;
    server 10.0.0.1:8080;
    server 10.0.0.2:8080;
    server 10.0.0.3:8080;
}

# IP Hash - 同じクライアントIPは同じサーバーへ(セッション固定)
upstream backend_iphash {
    ip_hash;
    server 10.0.0.1:8080;
    server 10.0.0.2:8080;
    server 10.0.0.3:8080;
}

# 重み付け(Weight)ベース
upstream backend_weighted {
    server 10.0.0.1:8080 weight=5;   # 50%トラフィック
    server 10.0.0.2:8080 weight=3;   # 30%トラフィック
    server 10.0.0.3:8080 weight=2;   # 20%トラフィック
}

# 高度な設定
upstream backend_advanced {
    least_conn;
    server 10.0.0.1:8080 weight=3 max_fails=3 fail_timeout=30s;
    server 10.0.0.2:8080 weight=2 max_fails=3 fail_timeout=30s;
    server 10.0.0.3:8080 backup;      # 他のサーバー障害時のみ使用
    server 10.0.0.4:8080 down;        # 一時的に無効化

    keepalive 32;                      # アップストリームコネクションプール
}

4.2 ロードバランシングアルゴリズム比較(ひかく)

アルゴリズム説明(せつめい)長所(ちょうしょ)短所(たんしょ)適(てき)した状況(じょうきょう)
Round Robin順次(じゅんじ)分配(ぶんぱい)(デフォルト)シンプル、均等(きんとう)分配サーバー性能差未反映同一(どういつ)スペックサーバー
Least Connections最小(さいしょう)接続数サーバーへ負荷(ふか)均衡(きんこう)新サーバーに集中(しゅうちゅう)可能リクエスト処理時間不均等
IP HashクライアントIPベースセッション固定(こてい)不均等分配の可能性セッションベースアプリ
Weight重み付けベース性能差反映手動管理サーバースペック差

4.3 ヘルスチェック

# パッシブヘルスチェック(OSS)
upstream backend {
    server 10.0.0.1:8080 max_fails=3 fail_timeout=30s;
    server 10.0.0.2:8080 max_fails=3 fail_timeout=30s;
}

5. SSL/TLS設定

5.1 Let's Encrypt + Certbot

# Certbotインストールと証明書発行
sudo apt install certbot python3-certbot-nginx
sudo certbot --nginx -d example.com -d www.example.com

# 自動更新確認
sudo certbot renew --dry-run

# crontabに自動更新追加
# 0 0,12 * * * certbot renew --quiet --post-hook "systemctl reload nginx"

5.2 強化(きょうか)SSL設定

# snippets/ssl-params.conf

# プロトコル - TLS 1.2, 1.3のみ許可
ssl_protocols TLSv1.2 TLSv1.3;

# 暗号化スイート
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
ssl_prefer_server_ciphers on;

# DHパラメータ
ssl_dhparam /etc/nginx/certs/dhparam.pem;

# SSLセッションキャッシュ
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 1d;
ssl_session_tickets off;

# OCSP Stapling
ssl_stapling on;
ssl_stapling_verify on;
ssl_trusted_certificate /etc/nginx/certs/chain.pem;
resolver 1.1.1.1 8.8.8.8 valid=300s;

# HSTS
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains; preload" always;

5.3 SSL Terminationパターン

Client (HTTPS)           Nginx (SSL Termination)         Backend (HTTP)
     │                          │                              │
HTTPS (TLS 1.3)        │                              │
     │─────────────────────────>│                              │
     │                          │  HTTP (plain)     │                          │─────────────────────────────>     │                          │                              │
     │                          │  HTTP Response     │                          │<─────────────────────────────│
HTTPS Response          │                              │
<─────────────────────────│                              │

6. キャッシング(Proxy Cache)

6.1 基本キャッシュ設定

http {
    # キャッシュゾーン定義
    proxy_cache_path /var/cache/nginx
        levels=1:2
        keys_zone=my_cache:10m      # 10MBメモリ(キー格納)
        max_size=10g                 # ディスク最大サイズ
        inactive=60m                 # 60分未使用で削除
        use_temp_path=off;

    server {
        listen 443 ssl http2;
        server_name example.com;

        # キャッシュ有効化
        location /api/ {
            proxy_cache my_cache;
            proxy_cache_valid 200 302 10m;    # 200, 302応答を10分
            proxy_cache_valid 404 1m;          # 404応答を1分
            proxy_cache_use_stale error timeout updating
                                   http_500 http_502 http_503 http_504;
            proxy_cache_background_update on;
            proxy_cache_lock on;

            # キャッシュキー設定
            proxy_cache_key "$scheme$request_method$host$request_uri";

            # キャッシュステータスヘッダー追加
            add_header X-Cache-Status $upstream_cache_status;

            proxy_pass http://backend;
            include snippets/proxy-params.conf;
        }

        # 静的ファイルキャッシュ(ブラウザ)
        location ~* \.(jpg|jpeg|png|gif|ico|css|js|woff2)$ {
            root /var/www/static;
            expires 30d;
            add_header Cache-Control "public, immutable";
            access_log off;
        }
    }
}

6.2 キャッシュステータス値

ステータス説明
HITキャッシュから応答提供
MISSキャッシュなし、バックエンドから取得
EXPIREDキャッシュ期限(きげん)切(き)れ、バックエンドから更新
STALE期限切れキャッシュだがstaleポリシーで提供
UPDATINGstale応答提供中、バックグラウンド更新
REVALIDATEDバックエンドが304応答、既存(きそん)キャッシュ再利用
BYPASSキャッシュバイパス設定によりバックエンド直接(ちょくせつ)リクエスト

7. Rate Limiting(速度(そくど)制限(せいげん))

7.1 基本Rate Limiting

http {
    # 制限ゾーン定義
    # 10MBメモリ、IPあたり毎秒10リクエスト
    limit_req_zone $binary_remote_addr zone=api_limit:10m rate=10r/s;

    # IPあたり毎秒1リクエスト(ログイン保護)
    limit_req_zone $binary_remote_addr zone=login_limit:10m rate=1r/s;

    # APIキーベースの制限
    limit_req_zone $http_x_api_key zone=apikey_limit:10m rate=100r/s;

    server {
        # APIエンドポイント - バースト許可
        location /api/ {
            limit_req zone=api_limit burst=20 nodelay;
            limit_req_status 429;

            proxy_pass http://backend;
        }

        # ログイン - 厳格(げんかく)な制限
        location /auth/login {
            limit_req zone=login_limit burst=5;
            limit_req_status 429;

            proxy_pass http://backend;
        }
    }
}

7.2 接続数(せつぞくすう)制限

http {
    # IPあたり同時接続数制限
    limit_conn_zone $binary_remote_addr zone=conn_limit:10m;

    server {
        # IPあたり最大100同時接続
        limit_conn conn_limit 100;

        # ダウンロード帯域(たいいき)制限
        location /downloads/ {
            limit_conn conn_limit 5;        # 5同時ダウンロード
            limit_rate 500k;                # 接続あたり500KB/s
            limit_rate_after 10m;           # 最初の10MBは制限なし
        }
    }
}

7.3 Rate Limitingの動作理解(りかい)

rate=10r/s, burst=20, nodelay:

時間  | リクエスト数 | 処理数 | 説明
─────│────────────│──────│──────────────────────────
0.0s │     252110(rate) + 20(burst) = 30まで許可
     │            │      │ 21件即時処理、4件が429応答
0.1s │      51  │ burstバケットに1つ空き(0.1s * 10r/s = 11.0s │      55  │ burstバケットが10個回復

8. WebSocketプロキシ

8.1 WebSocket設定

# WebSocketアップグレード用map
map $http_upgrade $connection_upgrade {
    default upgrade;
    ''      close;
}

upstream websocket_backend {
    server 10.0.0.1:8080;
    server 10.0.0.2:8080;

    # WebSocketはスティッキーセッションが必要
    ip_hash;
}

server {
    listen 443 ssl http2;
    server_name ws.example.com;

    ssl_certificate /etc/nginx/certs/fullchain.pem;
    ssl_certificate_key /etc/nginx/certs/privkey.pem;

    location /ws/ {
        proxy_pass http://websocket_backend;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection $connection_upgrade;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;

        # WebSocketタイムアウト(デフォルト60秒)
        proxy_read_timeout 3600s;
        proxy_send_timeout 3600s;
    }
}

8.2 WebSocketハンドシェイクフロー

Client                    Nginx                    Backend
  │                         │                         │
GET /ws/ HTTP/1.1       │                         │
Upgrade: websocket      │                         │
Connection: Upgrade     │                         │
  │────────────────────────>│                         │
  │                         │ GET /ws/ HTTP/1.1  │                         │ Upgrade: websocket      │
  │                         │ Connection: Upgrade  │                         │────────────────────────>  │                         │                         │
  │                         │ 101 Switching Protocols  │                         │<────────────────────────│
101 Switching Protocols │                         │
<────────────────────────│                         │
  │                         │                         │
<-- WebSocket frames -><-- WebSocket frames ->

9. セキュリティ設定

9.1 セキュリティヘッダー

server {
    # XSS保護
    add_header X-XSS-Protection "1; mode=block" always;

    # MIMEタイプスニッフィング防止
    add_header X-Content-Type-Options "nosniff" always;

    # クリックジャッキング防止
    add_header X-Frame-Options "SAMEORIGIN" always;

    # リファラーポリシー
    add_header Referrer-Policy "strict-origin-when-cross-origin" always;

    # Content Security Policy
    add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline' cdn.example.com; style-src 'self' 'unsafe-inline'; img-src 'self' data: cdn.example.com;" always;

    # Permissions Policy
    add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always;
}

9.2 アクセス制御(せいぎょ)

server {
    # IPベースのアクセス制御
    location /admin/ {
        allow 10.0.0.0/8;
        allow 192.168.0.0/16;
        deny all;

        proxy_pass http://backend;
    }

    # Basic認証
    location /internal/ {
        auth_basic "Restricted Access";
        auth_basic_user_file /etc/nginx/.htpasswd;

        proxy_pass http://backend;
    }

    # 特定HTTPメソッドのみ許可
    location /api/ {
        limit_except GET POST PUT DELETE {
            deny all;
        }

        proxy_pass http://backend;
    }

    # サーバー情報(じょうほう)隠蔽(いんぺい)
    server_tokens off;

    # 隠しファイルアクセスブロック
    location ~ /\. {
        deny all;
        access_log off;
        log_not_found off;
    }
}

9.3 基本的(きほんてき)なDDoS防御(ぼうぎょ)

http {
    # 接続制限
    limit_conn_zone $binary_remote_addr zone=conn_per_ip:10m;
    limit_req_zone $binary_remote_addr zone=req_per_ip:10m rate=30r/s;

    # リクエストボディサイズ制限
    client_max_body_size 10m;
    client_body_buffer_size 128k;
    client_header_buffer_size 1k;
    large_client_header_buffers 4 4k;

    # タイムアウト設定
    client_body_timeout 12;
    client_header_timeout 12;
    send_timeout 10;

    server {
        limit_conn conn_per_ip 50;
        limit_req zone=req_per_ip burst=50 nodelay;
    }
}

10. 圧縮(あっしゅく)とパフォーマンス最適化(さいてきか)

10.1 Gzip詳細(しょうさい)設定

http {
    gzip on;
    gzip_vary on;
    gzip_proxied any;
    gzip_comp_level 5;          # 1-9(5が最適バランス)
    gzip_min_length 1024;       # 1KB以下は圧縮しない
    gzip_buffers 16 8k;
    gzip_http_version 1.1;
    gzip_types
        text/plain
        text/css
        text/xml
        text/javascript
        application/json
        application/javascript
        application/xml
        application/xml+rss
        application/atom+xml
        image/svg+xml
        font/opentype
        font/ttf
        font/woff
        font/woff2;

    # 事前圧縮ファイルの使用(ビルド時生成)
    gzip_static on;
}

10.2 パフォーマンスチューニングチェックリスト

worker_processes auto;                # CPUコア数
worker_rlimit_nofile 65535;

events {
    worker_connections 10240;
    multi_accept on;
    use epoll;
}

http {
    # ファイル転送最適化
    sendfile on;
    tcp_nopush on;                    # sendfileと併用
    tcp_nodelay on;                   # keepaliveで有効

    # タイムアウト
    keepalive_timeout 65;
    keepalive_requests 1000;

    # バッファ
    client_body_buffer_size 16k;
    client_header_buffer_size 1k;
    client_max_body_size 50m;
    large_client_header_buffers 4 8k;

    # ファイルキャッシュ
    open_file_cache max=10000 inactive=20s;
    open_file_cache_valid 30s;
    open_file_cache_min_uses 2;
    open_file_cache_errors on;

    # アップストリームコネクションプール
    upstream backend {
        keepalive 32;
        keepalive_requests 100;
        keepalive_timeout 60s;
    }
}

11. DockerとKubernetes連携(れんけい)

11.1 Docker ComposeでNginx構成

# docker-compose.yml
version: '3.8'

services:
  nginx:
    image: nginx:alpine
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - ./nginx/nginx.conf:/etc/nginx/nginx.conf:ro
      - ./nginx/conf.d:/etc/nginx/conf.d:ro
      - ./nginx/certs:/etc/nginx/certs:ro
    depends_on:
      - app1
      - app2
    networks:
      - webnet
    restart: unless-stopped

  app1:
    image: myapp:latest
    expose:
      - "3000"
    networks:
      - webnet

  app2:
    image: myapp:latest
    expose:
      - "3000"
    networks:
      - webnet

networks:
  webnet:
    driver: bridge

11.2 Kubernetes Ingress(Nginx Ingress Controller)

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: my-app-ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
    nginx.ingress.kubernetes.io/ssl-redirect: "true"
    nginx.ingress.kubernetes.io/rate-limit: "10"
    nginx.ingress.kubernetes.io/rate-limit-window: "1m"
    nginx.ingress.kubernetes.io/proxy-body-size: "50m"
    cert-manager.io/cluster-issuer: "letsencrypt-prod"
spec:
  ingressClassName: nginx
  tls:
    - hosts:
        - example.com
        - api.example.com
      secretName: example-tls
  rules:
    - host: example.com
      http:
        paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: frontend-svc
                port:
                  number: 80
    - host: api.example.com
      http:
        paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: backend-svc
                port:
                  number: 8080

12. Nginx vs Traefik vs Caddy比較

機能(きのう)NginxTraefikCaddy
設定方式ファイルベース動的(Dockerラベル、K8s)Caddyfile / JSON API
自動HTTPS手動(Certbot)内蔵(ACME)内蔵(ACME)
サービスディスカバリ手動Docker/K8s自動制限(せいげん)的
パフォーマンス最高(さいこう)レベル良好(りょうこう)良好
HTTP/3モジュール対応内蔵内蔵
ダッシュボードなし(Nginx Plus有料(ゆうりょう))内蔵Web UI内蔵API
設定リロードnginx -s reload自動ホットリロード自動ホットリロード
適した環境(かんきょう)汎用(はんよう)、高性能マイクロサービス、Docker小規模(しょうきぼ)、簡単(かんたん)設定

12.1 選択(せんたく)ガイド

Nginxを選(えら)ぶべき場合(ばあい):

  • 最高のパフォーマンスと安定性(あんていせい)が必要な場合
  • 複雑(ふくざつ)なリバースプロキシルールが必要な場合
  • レガシーシステムや静的ファイル配信(はいしん)に最適

Traefikを選ぶべき場合:

  • Docker/Kubernetes環境で自動サービスディスカバリが必要な場合
  • 動的にルーティングルールが変更(へんこう)されるマイクロサービス環境

Caddyを選ぶべき場合:

  • 自動HTTPSが最も重要(じゅうよう)な場合
  • 簡単な設定で素早(すばや)く開始(かいし)したい場合

13. 面接対策(めんせつたいさく)クイズ

Q1. Nginxのイベント駆動アーキテクチャがApacheのプロセスモデルより有利(ゆうり)な理由(りゆう)は?

Apacheの従来(じゅうらい)のPrefork/Worker MPMは、各接続(かくせつぞく)にプロセスやスレッドを割(わ)り当(あ)てます。10,000の同時接続では10,000のプロセス/スレッドが必要で、それぞれ数MBのメモリを消費(しょうひ)します。

Nginxはイベントループベースで動作し、少数のWorkerプロセス(通常(つうじょう)CPUコア数)がepoll/kqueueなどのOSイベントメカニズムを通じて数万の接続を非同期的(ひどうきてき)に処理します。

核心的(かくしんてき)な違(ちが)い:

  • メモリ効率(こうりつ): Nginxは接続あたり数KB vs Apacheは接続あたり数MB
  • コンテキストスイッチ: Nginxは最小化 vs Apacheはプロセス/スレッド切替(きりかえ)オーバーヘッド
  • C10K問題: Nginxは設計(せっけい)段階(だんかい)からこの問題を解決するために作られた
Q2. proxy_passでのURIスラッシュ(/)の有無(うむ)による違いは?

これはNginx設定で最(もっと)も多(おお)い間違(まちが)いの一(ひと)つです。

proxy_pass http://backend;(スラッシュなし): リクエストURIがそのまま転送(てんそう)されます。/api/usersリクエストはバックエンドに/api/usersとして転送されます。

proxy_pass http://backend/;(スラッシュあり): locationにマッチした部分が除去(じょきょ)され、残(のこ)りが転送されます。

location /api/での例:

  • スラッシュなし: /api/usershttp://backend/api/usersに転送
  • スラッシュあり: /api/usershttp://backend/usersに転送

この違いを理解しないと、404エラーや誤(あやま)ったルーティングが発生(はっせい)します。

Q3. Rate Limitingのburstとnodelayオプションの役割は?

limit_req zone=api rate=10r/s burst=20 nodelay;

rate=10r/s: 毎秒10リクエストまで許可。内部的(ないぶてき)には100msごとに1リクエストを許可するトークンバケット方式です。

burst=20: rateを超過(ちょうか)するリクエストを最大20個までキューに待機(たいき)させます。burstなしではrate超過時に即座(そくざ)に429応答です。

nodelay: burstキューに入ったリクエストを遅延(ちえん)なく即座に処理します。nodelayなしではリクエストがrateに合わせて順次処理されるため待ち時間が発生します。

組み合(あ)わせ効果:

  • rate=10r/s burst=20: 瞬間(しゅんかん)最大21件処理可能だが、burstリクエストは遅延あり
  • rate=10r/s burst=20 nodelay: 瞬間最大21件を即座に処理、超過分は429
Q4. SSL Terminationとは何か、なぜ使用するのか?

SSL Termination(SSL終端(しゅうたん))は、HTTPS暗号化(あんごうか)/復号化(ふくごうか)をNginx(リバースプロキシ)で処理し、バックエンドサーバーには通常(つうじょう)のHTTPで通信(つうしん)するパターンです。

利点(りてん):

  1. バックエンド負荷(ふか)削減(さくげん): SSLハンドシェイクと暗復号化はCPU集約的(しゅうやくてき)作業。Nginxに集中(しゅうちゅう)
  2. 証明書(しょうめいしょ)管理の中央化(ちゅうおうか): すべての証明書をNginx一箇所(いっかしょ)で管理
  3. バックエンド簡素化(かんそか): バックエンドアプリケーションがSSLを気(き)にしなくてよい
  4. パフォーマンス最適化: NginxのSSLセッションキャッシュ、OCSP Staplingなどを活用

セキュリティ上(じょう)の考慮(こうりょ)事項(じこう):

  • Nginxとバックエンド間の内部(ないぶ)ネットワークが安全(あんぜん)でなければならない
  • 必要に応じて内部通信にもmTLS(Mutual TLS)を適用(てきよう)可能
Q5. upstreamのkeepaliveの役割と適切(てきせつ)な値は?

keepaliveは、Nginxとアップストリーム(バックエンド)サーバー間のアイドル接続をキャッシュするコネクションプールです。

upstream backend {
    server 10.0.0.1:8080;
    server 10.0.0.2:8080;
    keepalive 32;
}

keepaliveなし: 毎(まい)リクエストごとにTCP 3-wayハンドシェイクが発生。高負荷時にTIME_WAIT状態(じょうたい)のソケットが急増(きゅうぞう)してポート枯渇(こかつ)が発生する可能性があります。

keepaliveあり: 既存(きそん)の接続を再利用してTCPハンドシェイクオーバーヘッドを排除(はいじょ)。遅延(ちえん)時間削減とスループット向上(こうじょう)の効果(こうか)があります。

適切な値:

  • 同時接続数の約2倍が出発(しゅっぱつ)点(てん)
  • 高すぎるとメモリ浪費(ろうひ)、低すぎるとコネクション再利用効果が減少(げんしょう)
  • proxy_http_version 1.1;proxy_set_header Connection "";を一緒に設定する必要あり

14. 参考(さんこう)資料(しりょう)

  1. Nginx公式ドキュメント
  2. Nginx Admin Guide
  3. Nginx Plus機能比較
  4. Let's Encrypt / Certbot
  5. Nginx Ingress Controller
  6. Traefikドキュメント
  7. Caddyドキュメント
  8. Mozilla SSL Configuration Generator
  9. Nginxパフォーマンスチューニングガイド
  10. C10K Problem
  11. Nginx Cookbook (O'Reilly)
  12. DigitalOcean Nginxチュートリアル
  13. Nginxセキュリティベストプラクティス