このブログのウェブサーバーは記事作成現在OpenLiteSpeedを使っている。
OpenLiteSpeed+PHP7のページ表示速度はApache2+PHP7と比較してはるかに向上してるように感じる。
それはLiteSpeed自体の処理の速さに加えて新たにHTTP/2のServerPush機能を使っていることも大きいし、他にもウェブ管理画面が楽という個人的に大きなメリットがある。
(もちろんHTTP/2はApache2でもNginxでも使える)
これと言った不満もないため、うちの自宅サーバーのウェブサーバーもApache2からOpenLiteSpeedに乗り換えようと思ったのだが、フロントにNginxを置いてリバースプロキシとして使っているため、HTTP/2通信をする為にどのような設定が必要になるのか?という点で全て通して説明されている日本語の参考サイトが見当たらなかった。
本記事ではフロントエンドにNginx(リバースプロキシ)を置いてバックエンドにOpenLiteSpeedという構成でHTTP/2を使う設定を書く。
環境
Nginx,OpenLiteSpeedそれぞれにDebian Jessie(8.8)を新たにインストールして設定した。
Debian9だと記事作成時点ではLiteSpeedのPHP7がまだ対応されていないので注意。
Nginxには「ngx_http_v2_upstream」パッチを当てる必要がある。
また、Debian8.8のOpenSSLはデフォルトで1.0.1tだが、OpenSSL1.0.2以上である必要があるようだ。
- Nginx 1.13.2
- OpenLiteSpeed 1.4.26
- OpenSSL 1.0.2
[ktms_ads]
Nginxのビルド
Nginx側のインストールに関しては以下のページが非常に参考になった。
本記事の手順もほぼそのままなのだが、OpenLiteSpeedと組み合わせる上での修正や新たにインストールしないといけないパッケージがあるため、内容の重複はあるが詳細手順を書く。
必要パッケージのインストール
PCREライブラリとOpenSSLライブラリは新規インストールしたDebianではインストール必須だった。
何故かmakeもgccもcurlも入ってないので入れておく。
インストール
[bash]
sudo apt-get install mercurial libpcre3-dev libssl-dev make gcc curl
[/bash]
nginxのクローン作成
パッチファイルにあわせたバージョンにupdateする。
[bash]
hg clone http://hg.nginx.org/nginx/
cd ./nginx
hg update -r 7039
[/bash]
OpenSSL1.0.2のダウンロード
Debian8.8のOpenSSLは1.0.1tだが、諸々の事情で1.0.2が必要になる。
[bash]
wget https://www.openssl.org/source/openssl-1.0.2h.tar.gz
tar -xvzf openssl-1.0.2h.tar.gz
[/bash]
詳細が知りたい人は以下のページを参照。
パッチファイルの保存
NginxにGoogleの人が作ったパッチをあてる必要があるので保存しておく。
diffから終わりまでを1.patchから連番で保存する。
- [PATCH 01 of 14] Output chain: propagate last_buf flag to c->send_chain()
- [PATCH 02 of 14] Upstream keepalive: preserve c->data
- [PATCH 03 of 14] HTTP/2: add debug logging of control frames
- [PATCH 04 of 14] HTTP/2: s/client/peer/
- [PATCH 05 of 14] HTTP/2: introduce h2c->conf_ctx
- [PATCH 06 of 14] HTTP/2: introduce stream->fake_connection
- [PATCH 07 of 14] HTTP/2: introduce ngx_http_v2_handle_event()
- [PATCH 08 of 14] HTTP/2: add HTTP/2 to upstreams
- [PATCH 09 of 14] Proxy: add “proxy_ssl_alpn” directive
- [PATCH 10 of 14] Proxy: always emit “Host” header first
- [PATCH 11 of 14] Proxy: split configured header names and values
- [PATCH 12 of 14] Proxy: add HTTP/2 support
- [PATCH 13 of 14] Proxy: add “proxy_pass_trailers” directive
- [PATCH 14 of 14] Cache: add HTTP/2 support
次に先ほど保存したパッチファイルを順にあてていく。
パッチファイルのパスは保存場所に応じて適当に読み替える。
[bash]
patch -p1 < ./1.patch
patch -p1 < ./2.patch
patch -p1 < ./3.patch
patch -p1 < ./4.patch
patch -p1 < ./5.patch
patch -p1 < ./6.patch
patch -p1 < ./7.patch
patch -p1 < ./8.patch
patch -p1 < ./9.patch
patch -p1 < ./10.patch
patch -p1 < ./11.patch
patch -p1 < ./12.patch
patch -p1 < ./13.patch
patch -p1 < ./14.patch
[/bash]
ビルド
usernameをユーザー名に変更し、OpenSSL1.0.2ディレクトリへの正しいパスにすること。
[bash]
./auto/configure –with-http_ssl_module –with-http_v2_module –with-openssl=/home/username/openssl-1.0.2h
make
sudo make install
[/bash]
インストール場所や起動・停止など
aptでインストールしたNginxと違い、/usr/local/nginxにインストールされる。
[bash]
#起動
sudo /usr/local/nginx/sbin/nginx
#再起動
sudo /usr/local/nginx/sbin/nginx -s reload
#停止
sudo /usr/local/nginx/sbin/nginx -s stop
#バージョン確認
sudo /usr/local/nginx/sbin/nginx -V
[/bash]
aptでインストールしたNginxから設定を移植したい場合
DebianでNginxをapt-get installすると /etc/nginx にNginxがインストールされてconf.dディレクトリにリバースプロキシの設定を放り込むことになる。
今回ビルドしたNginxでは/usr/local/nginx/conf/nginx.confに全ての設定を書くことになるため、設定は全てnginx.conf内の適切な場所にコピペしてあげると動く。
(confディレクトリに持ってくるだけではダメ)
OpenLiteSpeedのインストール
インストールまではxx2zzの記事をそのまま使えばよいが、ビルド前に必要な処理があるので記す。
ビルド前に必要な処理
src/http/ntwkiolink.cpp を編集し、HTTP2_PLAIN_DEVを有効にする。
xx2zzの調査によると、HTTP2_PLAIN_DEVが無効のままビルドすると、強制的にHTTPとしてh2cのデータを処理しようとして400エラーが出る。
HTTP2_PLAIN_DEVを有効にすると、逆にHTTP/2以外の通信(HTTP, SPDY)を受け付けなくなることに注意。
65行目のコメントアウト(//)をはずす。
[cpp]
//#define HTTP2_PLAIN_DEV
↓
#define HTTP2_PLAIN_DEV
[/cpp]
実行ユーザー・グループを変更したい場合
そのままインストールすると、実行ユーザー・グループがnouser:nogroupになる。
これを任意のユーザー・グループ(例えばwww-data:www-data)に変更したい場合、ビルド時のオプションに「–with-user=www-data –with-group=www-data」を追加してやる事で指定できる。
[bash]
./configure –with-openssl=/usr –enable-http2 –with-user=www-data –with-group=www-data
[/bash]
HTTP/2通信するための設定(Nginx側)
パッチを当てたことにより「proxy_http_version 2.0;」が指定可能になる。
HTTPS化
NginxでLet’sEcnrypt証明書を取得するための設定を反映させる。
証明書を取得する過程でドキュメントルートに指定したディレクトリにファイルを作ってhttpで確認しにくるため、証明書取得のための設定を先に書く。
nginx.confの設定
[bash]
sudo vi /usr/local/nginx/conf/nginx.conf
server {
listen 80;
server_name ドメイン;
location ^~ /.well-known/acme-challenge {
root ドキュメントルート;
}
}
[/bash]
再起動して反映。
[bash]
sudo /usr/local/nginx/sbin/nginx -s reload
[/bash]
Let’sEncrypt証明書の取得
[bash]
apt-get install git
git clone https://github.com/letsencrypt/letsencrypt
cd letsencrypt
./letsencrypt-auto certonly –webroot -w ドキュメントルート -d ドメイン -m 適当なメールアドレス –agree-tos
openssl dhparam 2048 -out /etc/letsencrypt/live/ドメイン/dhparam.pem
[/bash]
HTTP/2を使うための設定
[bash]
sudo vi /usr/local/nginx/conf/nginx.conf
server {
proxy_http_version 2.0;
#証明書更新の際に80が必要
listen 80;
listen 443 ssl http2;
server_name ドメイン;
#Let’s Encrypt用
location ^~ /.well-known/acme-challenge {
root ドキュメントルート;
}
ssl_certificate /etc/letsencrypt/live/ドメイン/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/ドメイン/privkey.pem;
ssl_session_timeout 1d;
ssl_session_cache shared:SSL:50m;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_ciphers ‘ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-DSS-AES128-GCM-SHA256:kEDH+AESGCM:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-DSS-AES128-SHA256:DHE-RSA-AES256-SHA256:DHE-DSS-AES256-SHA:DHE-RSA-AES256-SHA:ECDHE-RSA-DES-CBC3-SHA:ECDHE-ECDSA-DES-CBC3-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:AES:CAMELLIA:DES-CBC3-SHA:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH-DSS-DES-CBC3-SHA:!EDH-RSA-DES-CBC3-SHA:!KRB5-DES-CBC3-SHA’;
ssl_prefer_server_ciphers on;
ssl_dhparam /etc/letsencrypt/live/ドメイン/dhparam.pem;
location / {
proxy_set_header Host $http_host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_pass LiteSpeedのIP;
}
}
[/bash]
再起動して反映。
[bash]
sudo /usr/local/nginx/sbin/nginx -s reload
[/bash]
HTTP2通信するための設定(LiteSpeed側)
管理画面にログインして設定を行う。
Nginx⇔LiteSpeed間はh2cなのでリスナーは80だけで良い。SSL証明書も関連の設定も不要。
- サーバー → 一般 → 「HTTP/2 Over Cleartext TCPを有効にする」を「はい」に
- リスナー → SSL → 「SPDY/HTTP2を有効にする」の「HTTP2」にチェックを入れる
その後バーチャルホスト設定を適当に行ってLiteSpeedを再起動する。
確認その他
HTTP/2が使えているか
HTTP/2が使えているかChromeのデベロッパーツールなんかで確認する。
Networkでプロトコルを表示させてh2になっていればOK。
ただし、Nginx-OpenLiteSpeed間はtcpdumpしないとわからない。
LiteSpeed側でクライアントIPを取得する
デフォルトだとログにはNginxのIPアドレスが記録されてしまう。
正しいクライアントIPを取得するためにはLiteSpeedの管理画面で以下の通り設定する。
- サーバー設定 → 一般 → 「ヘッダーにクライアントIPを使用する」を「はい」
なおNginx側で以下のヘッダーをセットする必要がある。
(この記事の通りに設定した場合はすでに書いてある)
[code]
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
[/code]
あとがき
以上でフロントエンドにNginx、バックエンドにOpenLiteSpeedという構成でHTTP/2が使えるようになった。
LiteSpeedは非常に軽くPHP7も普通に使えるのでお勧めできる。
無償版ではrewriteは使えてもhtaccessは使えないのだが、そのあたりに書きたいことは管理画面で設定したほうがむしろ楽だったりするのでApache2と比較してデメリットは感じない。
LiteSpeedに関しては以下の記事と被る部分はできるだけ省いたのでこちらも確認して欲しい。
コメント