PHP7.2.10をソースからインストールしphp-fpmの設定もする

OS: Ubuntu 18.04.1 LTS
Apache 2.4.34
PHP 7.2.10

まずはPHP7.2.10をソースコードからインストールする。wgetコマンドでダウンロードを試みたらファイル名がmirrorになってしまって参ったので--trust-server-namesオプションを付加しておくと良さそうである。

$ wget -c http://jp2.php.net/get/php-7.2.10.tar.bz2/from/this/mirror --trust-server-names
$ wget -c http://jp2.php.net/get/php-7.2.10.tar.bz2.asc/from/this/mirror --trust-server-names

$ gpg --recv-key DC9FF8D3EE5AF27F
$ gpg --verify php-7.2.10.tar.bz2.asc

$ tar jxvf php-7.2.10.tar.bz2
$ cd php-7.2.10/

configureスクリプトを実行してはエラーメッセージに足止めされ指定されたライブラリをaptでインストールするというルーチンを幾度も繰り返すのが常であるから、前もって入り用になると調べがついているライブラリは予めまとめて取り入れておくと後が大変気安い。

libcurl4についてはGnuTLS、NSS、OpenSSLという三種のフレーバーが揃い踏みであるけれども果たしてどれを選んだものか分からないのでひとまずGnuTLSフレーバーを選択した。autoconfはmake testを終えた後に結果のレポートをひとまず保存するために必要なだけであるからインストールはしなくとも差し障りがない。

メッセージ 必要なパッケージ
configure: error: libxml2 not found.
Please check your libxml2 installation.
libxml2-dev
checking for cURL 7.10.5 or greater…
configure: error: cURL version 7.10.5 or later
is required to compile php with cURL support
libcurl4-gnutls-dev
configure: error: jpeglib.h not found. libjpeg-dev
configure: error: png.h not found. libpng-dev
Do you want to send this report now? [Yns]: s
sh: 1: autoconf: not found
autoconf
$ sudo apt install libxml2-dev libcurl4-gnutls-dev libjpeg-dev libpng-dev autoconf

必要なライブラリをインストールしたら愈々configureスクリプトを実行する。FPM(FastCGI Process Manager)を有効にしたいので --enable-fpm の追加を忘れてはならない。あとは障りがなければインストールまですんなり捗る。なおmake testで33件失敗が発生していたけれども上位に位置するエラーばかりであったからよくある事として高を括ることに吝かでない。

$ ./configure --with-apxs2=/usr/local/apache2/bin/apxs --with-mysqli --with-openssl --with-zlib --enable-exif --with-gd --with-jpeg-dir --with-png-dir --with-zlib-dir --enable-mbstring --enable-pcntl --enable-soap --enable-zip --enable-fpm --enable-opcache --with-curl --enable-intl --with-pdo-mysql
$ make
$ make test
$ sudo make install

php.iniの雛形を指定のディレクトリへコピーして、ApacheがPHPのモジュールをロードするよう設定になっているか点検する。

$ sudo cp php.ini-development /usr/local/lib/php.ini
$ grep libphp7.so /usr/local/apache2/conf/httpd.conf
LoadModule php7_module        modules/libphp7.so

php-fpmを使用するための設定をおこなう。php-fpmにはApacheのモジュールmod_proxy_fcgi.soのロードが求められるしmod_proxy_fcgi.soにはmod_proxy.soが要求されるから共にロードするようhttpd.confを書き換える。

そしてSetHandlerディレクティブで以って、PHPスクリプトの全要求をリバースプロキシを用いて指定のFastCGIサーバーへ渡すよう設定する。てんで意味が呑み込めないけれどもPATH_INFOが最も正確であるという触れ込みであるから他の記述に比べ最も良さそうな情勢である。この記述はApache2.4.10から使用できるということであった。

$ sudo vi /usr/local/apache2/conf/httpd.conf
LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_fcgi_module modules/mod_proxy_fcgi.so

<FilesMatch "\.php$">
    # Note: The only part that varies is /path/to/app.sock
    #SetHandler  "proxy:unix:/path/to/app.sock|fcgi://localhost/"
    SetHandler  "proxy:unix:/home/guro/tmp/php/php-fpm.sock|fcgi://localhost/"
</FilesMatch>

<Proxy "fcgi://localhost/" enablereuse=on max=10>
</Proxy>

FPMのグローバルなオプションを記載する設定ファイルを雛形からコピーして書き換える。includeの箇所がNONEになっていてパスが有効でないから修正しておく。

$ cd /usr/local/etc/
$ sudo cp -av php-fpm.conf.default php-fpm.conf
$ sudo vi php-fpm.conf
;include=NONE/etc/php-fpm.d/*.conf
include=/usr/local/etc/php-fpm.d/*.conf

php-fpm.dディレクトリ内にプロセスプールの設定を個別に用意する。listenではFastCGIのリクエストを受け付けるアドレスを指定する。UNIXドメインソケットとTCPソケットの二種類から選択を迫られることになるけれどもUNIXドメインソケットのほうがパフォーマンスが優秀であるとほうぼうで評判であるから此れを選択する。

$ mkdir -p /home/guro/tmp/php
$ cd php-fpm.d/
$ sudo vi guro.conf
[guro]
user = guro
group = guro

listen = /home/guro/tmp/php/php-fpm.sock
listen.owner = guro
listen.group = guro
listen.mode  = 0666

pm = dynamic
pm.max_children = 5
pm.start_servers = 2
pm.min_spare_servers = 1
pm.max_spare_servers = 3

access.log = var/log/$pool.access.log
access.format = "%R - %u %t \"%m %r%Q%q\" %s %f %{mili}d %{kilo}M %C%%"
slowlog = var/log/$pool.log.slow
request_slowlog_timeout = 10

catch_workers_output = yes

設定が一段落したら文法の誤りをチェックする。ここで間違いが見つかればメッセージが現れるのからつぶさに調べて正す。

$ sudo /usr/local/sbin/php-fpm -t
[25-Sep-2018 06:51:03] ERROR: [/usr/local/etc/php-fpm.conf:125] unknown entry '#include'
[25-Sep-2018 06:51:03] ERROR: failed to load configuration file '/usr/local/etc/php-fpm.conf'
[25-Sep-2018 06:51:03] ERROR: FPM initialization failed

$ sudo /usr/local/sbin/php-fpm -t
[25-Sep-2018 06:52:01] NOTICE: configuration file /usr/local/etc/php-fpm.conf test is successful

文法テストに合格したら手動でphp-fpmを起動を試みると思惑通りに立ち上がって来ているようである。phpinfo()にもphp-fpmがactiveとして表示されているからまず間違いない様子である。

$ sudo /usr/local/sbin/php-fpm
$ ps axuwf | grep php-fp[m]
root      94279  0.0  0.3 192168 13044 ?        Ss   06:54   0:00 php-fpm: master process (/usr/local/etc/php-fpm.conf)
guro      94280  0.0  0.3 194468 12744 ?        S    06:54   0:00  \_ php-fpm: pool guro
guro      94281  0.0  0.3 194468 12744 ?        S    06:54   0:00  \_ php-fpm: pool guro

そうしたらどこへ出しても恥ずかしいコンテンツを設置して終いである。

参考:
PHP: Apache 2.x (Unixシステム用) – Manual
mod_proxy_fcgi – Apache HTTP Server Version 2.4
php-fpm.conf のグローバル設定項目

PHPでOPcacheを有効にする

OS: Ubuntu Server 18.04.1 LTS
PHP 7.2.10

ソースからインストールしたPHPのOPcacheを有効にしてパフォーマンスの向上を目論むものである。PHPをソースコードからコンパイルする際にconfigureオプションに--enable-opcacheが含まれていなければいけない。其れを前提としてphp.iniを編集する。

$ sudo vi /usr/local/lib/php.ini
[opcache]
zend_extension=/usr/local/lib/php/extensions/no-debug-zts-20170718/opcache.so
opcache.enable=1
opcache.enable_cli=1
opcache.memory_consumption=128
opcache.max_accelerated_files=10000
opcache.revalidate_freq=60

公式の文献ではopcache.fast_shutdown=1も推奨されているけれどもPHP7.2.0以降ではこのディレクティブはすっかり削除されてPHPに統合され、使用できそうなら自動的に適用されるということである。

opcache.fast_shutdown boolean
(snip)
このディレクティブは、PHP 7.2.0 で削除されました。 A variant of the fast shutdown sequence has been integrated into PHP and will be automatically used if possible.

CLI版のPHPで設定が有効になっているか否かを点検してみるとこういう具合であって首尾よくいっているようである。

$ php -v
PHP 7.2.10 (cli) (built: Sep 21 2018 01:44:12) ( ZTS )
Copyright (c) 1997-2018 The PHP Group
Zend Engine v3.2.0, Copyright (c) 1998-2018 Zend Technologies
    with Zend OPcache v7.2.10, Copyright (c) 1999-2018, by Zend Technologies

SAPI版のPHPの方は如何にと思ってphpinfo()を実行してみるとやはり有効になっている模様であった。定量的にパフォーマンスを計測していないけれども体感としてPHPアプリケーションがきりきり働いているように思えるのでもはや成功と云える。

参考:
OPcache > インストール/設定
OPcache 設定オプション

php.iniの正しい設置場所をあらためて確認する

OS: Ubuntu Server 16.04
Nginx 1.12.2
PHP 7.2.3

Nginxが稼働する環境へPHPをインストールするとなればNginx 1.4.x on Unix systemsの手続きを参照するのは無理からぬ事である。公式であるから全幅の信頼を寄せて盲目的に従うのもやはり無理からぬ事である。これが裏目に出た。第四番目の手続きである。

4. Obtain and move configuration files to their correct locations
cp php.ini-development /usr/local/php/php.ini

php.iniを/usr/local/php/へと配したのちに、OPcacheを有効にすべくphp.iniへ必要な記述をこなしてphp -vを実行するとこうである。

$ php -v
PHP 7.2.3 (cli) (built: Mar 17 2018 01:31:01) ( NTS )
Copyright (c) 1997-2018 The PHP Group
Zend Engine v3.2.0, Copyright (c) 1998-2018 Zend Technologies

「with Zend OPcache v7.2.3, Copyright (c) 1999-2018, by Zend Technologies」が出力に表れないのでOPcacheが有効になっていない模様である。テストスクリプトの実行結果も「PHP Fatal error: Uncaught Error: Call to undefined function opcache_get_status()」とあるからまったく狼狽した。いくらインターネットのページを繰っても似たような状況に遭遇した人が見当たらないのでどうやら世界ではじめて犯したヘマである。情けない。さんざ調べた末、結局はphp.iniの設置場所が良くないようで/usr/local/libへと移動させることで解決を見た。

$ sudo mv /usr/local/php/php.ini /usr/local/lib/
$ php -v
PHP 7.2.3 (cli) (built: Mar 17 2018 01:31:01) ( NTS )
Copyright (c) 1997-2018 The PHP Group
Zend Engine v3.2.0, Copyright (c) 1998-2018 Zend Technologies
    with Zend OPcache v7.2.3, Copyright (c) 1999-2018, by Zend Technologies

configureのヘルプからも特別に指定しなければ/usr/local/libにphp.iniを求めにゆくことが明らかである。

$ ./configure --help
(snip)
  --prefix=PREFIX         install architecture-independent files in PREFIX
                          [/usr/local]
  --with-config-file-path=PATH
                          Set the path in which to look for php.ini [PREFIX/lib]

またphp -iの実行結果から現在の設定を確かめることができるから、php.iniの設定が反映されずどうも様子がおかしいと感ずるときは確認をするのが良さそうである。

$ php -i | grep php.ini
Configuration File (php.ini) Path => /usr/local/lib
Loaded Configuration File => /usr/local/lib/php.ini

参考:
Nginx 1.4.x on Unix systems