page_adsence

2016年5月25日水曜日

PHPのバージョンアップに伴うPHP関連の調査メモ

PHPを5.2系から5.6系にバージョンアップするにあたって、諸々調査してみました。
  • php.ini関連(主にAPC- > APCu + OPCacheへの移行に関して)
  • php-fpmの設定値に関して
  • mysqlndの利用可・不可

php.ini関連(主にAPC- > APCu + OPCacheへの移行に関して)

APCはPHP 5.5以降では利用できなくなってしまったため、APCu + OPCacheに乗り換える必要があります。
乗り換えるにあったって、諸々調査したのでその結果を残しておこうと思います。

APC(Alternative PHP Cache)

まずAPCとは「Alternative PHP Cache (APC) は、PHP の実行コードをキャッシュする仕組みで、 フリーかつオープンに使用できます。PHP の中間コードのキャッシュ・最適化を行うための、フリーでオープンかつ堅牢なフレームワークを提供するということを目標としています。」(PHPの公式から抜粋)
と書かれていますが、実際は中間コードのキャッシュだけではなく、インメモリ型のKVSとして利用することも可能です。
※但しネットワーク越しのアクセスは不可

APCu

APCu is APC stripped of opcode caching.
→ APCuはAPCのオペコードキャッシュを除いたものです。

The first APCu codebase was versioned 4.0.0, it was forked from the head of the APC master branch at the time.
→ APCuの最初のコードはバージョン4.0.0で、APCのマスターブランチをフォークして作成されています。

PHP 7 support is available as of APCu 5.0.0.
→ PHP 7はAPCu5.0.0が利用出来る様になっています。

APCu can provide a compatibility mode, such that it can provide a drop in replacement for the applicable parts of APC.
→ APCuは互換性モードを提供しており、APCの一部の機能の下位互換を持っています。

公式から抜粋して訳してみたのですが、合っている保証はありません。
要するにインメモリ型のKVSの機能のみを提供するもので、APCからフォークされて出来ているみたいです。

OPCache(Zend OPCache)

OPCacheは「OPcache はコンパイル済みのバイトコードを共有メモリに保存し、PHP がリクエストのたびにスクリプトを読み込み、パースする手間を省くことでパフォーマンスを向上させます。」
と記載されている通りの機能です。
1点問題になるのは、OPCacheはシンボリックリンクを解決した状態でキャッシュされるため、
シンボリックリンクを変更しても、キャッシュは更新されないという問題がある。

http://kohkimakimoto.hatenablog.com/entry/2014/09/13/154342

また、opcache_resetもCLIから実行するとCLI側のオペコードキャッシュしか消えないようです。
そしてWebから実行されたopcache_resetはWeb側もCLI側も消えるという・・・。
この辺は自分でも検証してみようと思います。
結果は後日追記する予定です。

http://tech.gmo-media.jp/post/136590171029/php-53-to-php-56

php-fpm(FastCGI Process Manager)の設定値に関して

「PHP の FastCGI 実装のひとつで、 主に高負荷のサイトで有用な追加機能を用意しています。」 各サーバのスペックに応じてチューニングする必要のある部分は下記の所になります。(下記はデフォルト値です)
項目名設定値
pm.max_children50
pm.start_servers5
pm.min_spare_servers5
pm.max_spare_servers35
pm.max_requestsコメントアウト

この辺の値を変更する必要があるのですが、一律で変更出来るものではないので、
各自負荷テストを行った結果を反映させる必要があります。

mysqlndの利用可・不可

mysqlnd「MySQL Native Driver」とは「MySQL Client Library」に変わる新たなライブラリです。
mysqlndにしかない機能も多数あるので、移行出来るものならしたいものですが、そうはいかない世の中でした。
php5.5以降からmysqlndがデフォルトで利用される様になったのですが、mysqlndで16バイト長のパスワードが設定されているMySQL Serverに接続しにいくと、エラーが出てしまい接続出来ないという現象が発生します。
現状稼働しているMySQLに接続しにいかないといけないとかがあると、一手間必要になってしまいます。
どういった事が必要になるかというと、mysqlndでは41バイト長のパスワードハッシュでないと接続出来ないので、
バージョンの古いMySQLのバージョンだと、16バイト長のパスワードハッシュになっているので、それを41バイトハッシュに書き換えてやる必要があります。
影響範囲の洗い出しが簡単で、DB停止とかが出来るのであれば、変更可能だとは思いますが、そうでない場合は簡単には踏み切れないですね・・・。
PHP5.2(libmysql)とPHP5.6(mysqlnd)で、それぞれ16バイトと41バイトのパスワードが設定されている時にどういった挙動になるかを表にしてみました。
PHP5.2.17(libmysql)PHP5.6.18(mysqlnd)
MySQL5.1 [16byte Password]OKNG(mysqlnd cannot connect)
MySQL5.6 [16byte Password]OKNG(パスワード不一致)
MySQL5.1 [41byte Password]OKOK
MySQL5.6 [41byte Password]OKOK

基本的にはパスワードさえ41バイト長のものに変えてしまえばログイン出来るのですが、
注意点としては、MySQL4.0以前のクライアントが残っていると41バイト長のパスワードは受け付けられないので、ログインできなくなります。(下記の様なエラーが出るみたいです)
> mysql -h localhost -u root
Client does not support authentication protocol requested
by server; consider upgrading MySQL client
とはいえ、MySQL5.7では16バイト長のパスワード(OLD_PASSWORD)のサポートがなくなるみたいですので、早めに移行するに越したことはないですね。
既存のデータベースに引っ張られない様なシステムの構築する場合は、積極的に使っていきたいと思います。