0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Nginx の設定に疲れたら Caddy に移行しよう — 設定ファイル比較と移行手順

0
Posted at

Nginx の設定に疲れたら Caddy に移行しよう — 設定ファイル比較と移行手順

TL;DR

  • Nginx の SSL 設定・certbot 更新・proxy_set_header の記述量に疲れた人向け
  • Caddy はドメイン名を書くだけで自動 HTTPS + リバースプロキシが完成する
  • Nginx → Caddy の移行手順を 3 パターン(単一サーバー・複数サービス・WebSocket)で解説

動作確認環境

  • Ubuntu 24.04 LTS
  • Caddy v2.9.x
  • 移行元: Nginx 1.24.x + certbot
# Caddy インストール(Ubuntu/Debian)
sudo apt install -y debian-keyring debian-archive-keyring apt-transport-https
curl -1sLf 'https://dl.cloudsmith.io/public/caddy/stable/gpg.key' | sudo gpg --dearmor -o /usr/share/keyrings/caddy-stable-archive-keyring.gpg
curl -1sLf 'https://dl.cloudsmith.io/public/caddy/stable/debian.deb.txt' | sudo tee /etc/apt/sources.list.d/caddy-stable.list
sudo apt update
sudo apt install caddy

なぜ Nginx から Caddy に移行するのか

設定量の差を見てほしい

Nginx: SSL + リバースプロキシ(19行)

server {
    listen 80;
    server_name example.com;
    return 301 https://$server_name$request_uri;
}

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

    ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
    ssl_protocols TLSv1.2 TLSv1.3;
    ssl_ciphers HIGH:!aNULL:!MD5;

    location / {
        proxy_pass http://localhost:3000;
        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;
    }
}

Caddy: 同じことをする設定(2行)

example.com {
    reverse_proxy localhost:3000
}

Caddy はドメイン名を書くだけで以下を自動で行う:

  • Let's Encrypt から SSL 証明書を取得
  • 証明書の自動更新(期限 30 日前)
  • HTTP → HTTPS リダイレクト
  • 適切な proxy_set_header 相当のヘッダー付与
  • HTTP/2 対応
  • OCSP ステープリング

certbot の cron 設定も不要。ssl_protocolsssl_ciphers の選定も不要。

移行パターン 1: 単一サービス

最もシンプルなケース。Next.js や Express が 1 つ動いている場合。

Before(Nginx)

# /etc/nginx/sites-enabled/myapp
server {
    listen 80;
    server_name myapp.example.com;
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    server_name myapp.example.com;
    ssl_certificate /etc/letsencrypt/live/myapp.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/myapp.example.com/privkey.pem;

    location / {
        proxy_pass http://127.0.0.1:3000;
        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;
    }
}

After(Caddy)

# /etc/caddy/Caddyfile
myapp.example.com {
    reverse_proxy 127.0.0.1:3000
}

移行コマンド

# 1. Nginx を停止(port 80/443 を解放)
sudo systemctl stop nginx
sudo systemctl disable nginx

# 2. Caddyfile を作成
sudo tee /etc/caddy/Caddyfile << 'EOF'
myapp.example.com {
    reverse_proxy 127.0.0.1:3000
}
EOF

# 3. Caddy を起動
sudo systemctl enable caddy
sudo systemctl start caddy

# 4. 証明書の自動取得を確認(数秒で完了)
sudo journalctl -u caddy --no-pager -n 20
# "certificate obtained successfully" が出れば OK

移行パターン 2: 複数サービス

API サーバー + フロントエンド + 管理画面など、1 台のサーバーで複数サービスを動かしている場合。

Before(Nginx)

# api.example.com
server {
    listen 443 ssl http2;
    server_name api.example.com;
    ssl_certificate /etc/letsencrypt/live/api.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/api.example.com/privkey.pem;
    location / {
        proxy_pass http://127.0.0.1:8080;
        # ... header 設定省略
    }
}

# app.example.com
server {
    listen 443 ssl http2;
    server_name app.example.com;
    ssl_certificate /etc/letsencrypt/live/app.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/app.example.com/privkey.pem;
    location / {
        proxy_pass http://127.0.0.1:3000;
        # ... header 設定省略
    }
}

# admin.example.com
server {
    listen 443 ssl http2;
    server_name admin.example.com;
    ssl_certificate /etc/letsencrypt/live/admin.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/admin.example.com/privkey.pem;
    location / {
        proxy_pass http://127.0.0.1:4000;
        # ... header 設定省略
    }
}

After(Caddy)

api.example.com {
    reverse_proxy 127.0.0.1:8080
}

app.example.com {
    reverse_proxy 127.0.0.1:3000
}

admin.example.com {
    reverse_proxy 127.0.0.1:4000
}

3 ドメイン分の SSL 証明書が自動で取得・更新される。certbot の --expand オプションとの格闘が不要になる。

移行パターン 3: WebSocket 対応

チャットアプリや Socket.IO を使っているサービスの場合。

Before(Nginx)

server {
    listen 443 ssl http2;
    server_name ws.example.com;
    # ... SSL 設定省略

    location / {
        proxy_pass http://127.0.0.1:3001;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_set_header Host $host;
        proxy_read_timeout 86400;
    }
}

After(Caddy)

ws.example.com {
    reverse_proxy 127.0.0.1:3001
}

Caddy は WebSocket のアップグレードを自動で処理する。proxy_http_versionUpgrade ヘッダーの設定は不要。

注意点

Caddy が向かないケース

  • 超高負荷(10 万 req/s 以上): Nginx の方がチューニングの余地が大きい
  • 複雑なルーティングルール: location の正規表現マッチが多用されている場合、Caddy の handle + path に変換する手間がある
  • 既存の Nginx モジュール依存: Lua モジュールなど Nginx 固有の機能を使っている場合

certbot の証明書は削除してよいか

Caddy に移行したら certbot の証明書は不要。ただし、すぐに削除せず 1 週間ほど Caddy の自動取得が安定しているか確認してから削除するのが安全。

# Caddy の証明書状態確認
sudo caddy list-certs
# または
sudo journalctl -u caddy | grep -i "certificate"

まとめ

項目 Nginx Caddy
SSL 設定 certbot + cron + 手動設定 自動(ゼロ設定)
設定ファイル量 多い 少ない
WebSocket 明示的な設定が必要 自動対応
パフォーマンス 超高負荷向け 中〜高負荷で十分
学習コスト 高い 低い

個人開発やスタートアップ規模のサーバーなら、Caddy に移行するメリットは大きい。設定ファイルのメンテナンスコストが劇的に下がる。

Caddy のロードバランシング、キャッシュ戦略、セキュリティヘッダーなど、リバースプロキシの全機能については Caddy v2リバースプロキシ設定ガイド — 自動HTTPSで簡単構築 でまとめています。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?