NginxとLet's EncryptでHTTPS化する手順

CertbotとLet's Encryptを使ってNginxサーバーをHTTPS化する手順を、設定ファイルの例と自動更新の設定まで含めて解説します。

前提


Certbotのインストール

1
2
sudo apt update
sudo apt install certbot python3-certbot-nginx -y

証明書の取得

1
sudo certbot --nginx -d example.com -d www.example.com

Certbotがドメインの所有確認(ACMEチャレンジ)を行い、証明書を自動取得します。その際、Nginxの設定ファイルも自動で書き換えてくれます。

取得に成功すると証明書は /etc/letsencrypt/live/example.com/ に配置されます。


Nginxの設定例

Certbotが自動設定しますが、手動で管理する場合のテンプレートです。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
server {
    listen 80;
    server_name example.com www.example.com;
    # HTTPはHTTPSへリダイレクト
    return 301 https://$host$request_uri;
}

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

    ssl_certificate     /etc/letsencrypt/live/example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;

    # セキュリティヘッダー
    add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;
    add_header X-Content-Type-Options nosniff;
    add_header X-Frame-Options DENY;

    # TLSバージョンの制限
    ssl_protocols TLSv1.2 TLSv1.3;
    ssl_prefer_server_ciphers on;

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

X-Forwarded-Proto ヘッダーをアプリ側に渡すのを忘れずに。アプリがHTTPSかどうかを判断するために使います。


設定の反映とテスト

1
2
3
4
5
# 設定ファイルの構文チェック
sudo nginx -t

# 設定の反映
sudo systemctl reload nginx

自動更新の確認

Let's Encryptの証明書は90日で期限切れになりますが、Certbotをインストールすると自動更新のsystemdタイマーが設定されます。

1
2
3
4
5
# タイマーの状態確認
sudo systemctl status certbot.timer

# 手動で更新テスト(実際には更新しない)
sudo certbot renew --dry-run

--dry-run でエラーが出なければ自動更新も正常に動作します。


SSL評価の確認

設定後は SSL Labs でスコアを確認するのがおすすめです。上記の設定であればAまたはA+が取れるはずです。

ポイントは以下の3点です。

  1. TLS 1.0/1.1を無効化してTLS 1.2以上に限定する
  2. Strict-Transport-Security ヘッダーでHSTSを有効化する
  3. 強力な暗号スイートを優先する

よくあるトラブル

certbot が 80番ポートに接続できない

ufwで80番ポートが閉じているケースがあります。

1
2
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp

ドメインが解決できない

AレコードのDNS反映には時間がかかります。dig example.com A でサーバーのIPが返ってくるまで待ちます。

Nginx の設定ファイルが複数ある

/etc/nginx/sites-enabled/ 内の設定が競合していないか確認します。

1
sudo nginx -T | grep server_name

まとめ

作業コマンド
証明書取得certbot --nginx -d example.com
構文チェックnginx -t
設定反映systemctl reload nginx
更新テストcertbot renew --dry-run
自動更新確認systemctl status certbot.timer

HTTPSはもはや必須です。Let's EncryptとCertbotの組み合わせであれば無料で自動的に維持できるため、HTTP運用を続ける理由はありません。