はじめに
先日リリースされていたNGINX Unitについて、WordPressを動かしたかったです。
先日はNGINX Unitを動かすところまでできていたので、そこからWordPressを動かすようにしました。
最新版を拾ってくる
先日試した感じだとUnitではWordPressが動きませんでした。
@seiyakubo さんの記事が参考になりました。バージョン0.1(現行の最新版)だとPOSTが送れないため、殆どのPHPアプリケーションが動かないらしいです。
NGINX UnitでWordpressを動かしてみたけど動かなかった
最新masterブランチだと動くらしかったので、そちらからソースをコピーしました。
DockerでNGINX Unitのコンテナを作る
前回のコードからNGINX Unit用のコンテナを作ります。
FROM ubuntu:16.04
RUN apt update -y && \
apt install -y emacs-nox zsh mlocate git sudo net-tools build-essential
COPY nginx_signing.key /root/nginx_signing.key
RUN apt-key add /root/nginx_signing.key
RUN echo "deb http://nginx.org/packages/mainline/ubuntu/ xenial nginx\n deb-src http://nginx.org/packages/mainline/ubuntu/ xenial nginx" >> /etc/apt/sources.list
RUN apt update -y
#RUN apt install -y unit
RUN apt install -y nginx
RUN apt install -y php-dev libphp-embed php7.0-mysql mysql-client
RUN git clone https://github.com/nginx/unit /tmp/unit && \
cd /tmp/unit && \
git checkout 8e2fd89634bedd4570a2d3d885c209a0e1d20d62 && \
./configure --prefix=/opt/unit && \
./configure php && \
make && \
make install
RUN apt install -y composer
RUN service nginx start
CMD ["/opt/unit/sbin/unitd", "--no-daemon", "--control", "unix:/var/run/control.unit.sock"]
## 何もしないDockerにするときはこれ
# CMD ["sleep","3600"]
この中のgit clone
〜あたりで最新版のNGINX Unitのコードを拾っています。
またunit
起動時に--control unix:/var/run/control.unit.sock
オプションを与えることで、UNIXソケットの場所を指定します。
この指定がないと./configure
で指定される/opt/unit
辺りにソケットファイルが置かれることになります。
こちらでもかまわないのですが、混乱を避けるため/var/runに指定しておきます。
またNGINX周りのインストールも行っています。
NGINX Unitは単体ではアプリケーションを動かすのみで、HTTPサーバ機能は提供されていません。
その為、リバースプロキシとしてNGINXをインストールしています。
Dockerイメージをビルドします。
$ docker build --rm ./ -t yousan/nginx-unit
このイメージはこちらのものと同様です。
docker-compose
今回はWordPressを使うことが目的のため、MySQL(MariaDB)も一緒に動かします。
docker-composeを使って両方を起動させます。
version: '2'
services:
nginx-unit:
image: yousan/nginx-unit
container_name: nginx-unit
ports:
- 8300:8300
volumes:
- ./json:/root/json
- ./run:/var/run
- ./root:/www/root
- ./conf/php.ini:/etc/php/7.0/embed/php.ini
- ./conf/default.conf:/etc/nginx/conf.d/default.conf
mysql:
image: mariadb
environment:
MYSQL_ROOT_PASSWORD: example
ports:
- 3306:3306
volumes:
- ./mysql:/var/lib/mysql
HTTPアクセスをNGINXに接続させるため、ポート番号をバインドしています。
またNGINX、PHPのコンフィグファイル、NGINX Unitの制御用jsonファイル、ドキュメントルートをローカル側で編集させるため、ボリュームをマウントしています。
起動します。
$ docker-compose up -d
動きましたね。
コマンドの送信
NGINX UnitではHTTPリクエストを使って起動、設定などを行います。
通常のHTTPリクエストはTCP/IPを利用していますが、NGINX Unitの制御に使用するHTTPリクエストはUNIXソケットファイルを使います。
コマンドではcurl --unix-socket
で指定される引数で接続が指定されます。
今回はDockerの中でNGINX Unitが起動していますので、このソケットファイルを利用する必要があります。
しかしMacOSのDockerではUNIXソケットファイルを共有することができないため、そのままでは通信することができません。
そこでDockerコンテナの中でcurlコマンドを使い、HTTPリクエストを投げてみます。
先ほどdocker-compose.yamlで指定しておいたjson
ディレクトリには、起動用のJSONファイルを置いてあります。
{
"listeners": {
"*:8300": {
"application": "blogs"
}
},
"applications": {
"blogs": {
"type": "php",
"workers": 20,
"root": "/www/root",
"index": "index.php"
}
}
}
このファイルを使ってHTTPリクエストを送ります。コンテナの内部でcurl
コマンドを動かすため、パスの表記に注意が必要です。
$ docker-compose exec nginx-unit curl -X PUT -d @/root/json/start.json --unix-socket /run/control.unit.sock http://localhost/
{
"success": "Reconfiguration done."
}
うまく動きました。
コンテナの中から送る方法
もちろんコンテナ内部に入って送ることもできます。
/bin/bash
でコンテナ内部に入り、先ほどと同じコマンドを送信します。
$ docker-compose exec nginx-unit /bin/bash
# curl -X PUT -d @/root/json/start.json --unix-socket /run/control.unit.sock http://localhost/
確認
ブラウザで接続して動作を確認しておきます。
ここでは試験用にphpinfo()
を表示させています。
<?php phpinfo();
WordPressの設定
WordPressの本体はPHPファイルです。
今回はroot
というディレクトリをドキュメントルートにしているため、そちらにコアファイルを設置します。
composerを使ってインストールします。
{
"require": {
"php": ">=5.4",
"johnpbloch/wordpress": "4.7.5"
},
"extra": {
"wordpress-install-dir": "wp/"
}
}
composer install
でコアファイルをダウンロード、インストールします。
rootディレクトリはバインドされているため、このcomposer
コマンドはローカル側、ホスト側どちらで動かしても良いです。
@Hiraku さんのprestissimoの導入ですとか、そのあたりをローカル側で行っているため、ローカルで動かしました。
光遅い問題を克服してcomposerを10倍速くした話
インストールが完了したらMySQLのデータベースを作っておきます。
$ docker-compose exec mysql mysqladmin create -hlocalhost -uroot -ppassword root_wordpress
確認
ここまでできたら後は動作確認です。
wp/
ディレクトリにインストールしているので、そちらを参照します。
初期ユーザなどの設定が完了すれば動きます。
お疲れ様です!
まとめ
NGINX Unitは有料版がでるそうですね。今後はPHP-FPM、HHVMなどを置き換えていくほどのすごいアプリケーションになるのか、なにせNGINX謹製のアプリケーションサーバですからその性能に期待して胸が膨らみます。
数台、数百台の仮想インフラ上にアプリケーションユニットをポコポコならべて並列化させて…、もしくはユニットを単位としてAWSとかで提供されて…、なのかもしれませんね!
あと結局Dockerfileは華麗じゃないので書き直せるといいな。
参考
http://hatebu.me/entry/2017/09/08/200539
https://www.nginx.com/blog/introducing-nginx-application-platform/