筆者の周囲だけかもしれませんが、さいきんGoogle App Engine Standard Environment(以下GAE/SE)が再注目されつつあるように思います。今回筆者もgVisorベースのGAE/SE PHP 7.2環境に触ってみたので、その内容を紹介します。
GAE/SEとは
GAE/SEは元祖PaaSとも言えるような、Googleが提供するフルマネージド環境です。以前からJava、Python、Go、PHPの4言語の環境が提供されていましたが、Go以外の言語のバージョンアップは長いこと提供されておらず、Googleの本気度に疑問に持っていた人も多かったように思います(私もその一人でした)。
ところが最近になってNode.js 8、Java 8、Python 3.7、PHP 7.2と立て続けに新バージョンを提供してきており、Googleが水面下でGAE/SEに開発リソースを投入していたことが明らかになってきました。
この急ピッチの言語提供に一役買っているのが新サンドボックス実装であるgVisorです。私のざっくりの理解ではLinuxのシステムコール類をユーザーランドで提供するようなもので、既に多くのOSSが修正なしで動くような対応状況になっているようです。このgVIsorはGoでフルスクラッチ実装されており、ソースコードも公開されています。
旧サンドボックスのGAE/SE PHP 5.5環境とPHP 7.2環境の違い
以前のGAE/SE PHP 5.5環境を使ったことがある人は、GAEは制約が強い環境だという印象があるかもしれません。実際、旧サンドボックス上で動作しているPHP 5.5環境には次のような制約がありました。
- PHP本体にかなり大きなパッチが当たっている
- PHPから読めるディレクトリが非常に少ない
- 自分のデプロイしたファイルくらいしか見えない
- PHPから書き込めるディレクトリはおそらく無い
- ファイルを作りたい場合GCSに書く必要がある
- コマンド実行が許可されていない
- そもそもプロセスが実装されていない可能性すらある
特にファイル操作とコマンド実行の制約が大きく、既存のPHPアプリケーションがそのまま動くとは言いがたい状況でした。
一方、PHP 7.2環境は次のような状況です。
- 普通のPHPが動いている
- SAPIはphp-fpm
- PHPから全ファイルが見える
/tmp
がtmpfsになっており、PHPから書き込める- コマンド実行ができる
- わりと普通のLinux環境っぽい
/proc
や/dev
がある(まだ少し足りていない雰囲気)
旧サンドボックス環境に比べれば圧倒的に普通の環境と言えそうです。PHP 5.5時代にGAEは厳しいなーと思った人がいたとしても、今回は当時とは全然違う印象になるのではないでしょうか。
PHP 7.2環境の各種コマンドの実行結果
いくつかのコマンドを試した中から面白かったものを紹介します。
ps aux
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND root 1 0.3 0.2 13488 5620 ? Ssl 17:11 0:00 serve index.php root 14 1.0 4.2 265716 88352 ? Ss 17:11 0:00 php-fpm: master process (/tmp/serve-361831195/php-fpm.conf) root 15 0.8 3.0 266060 63724 ? S 17:11 0:00 php-fpm: pool app root 16 2.4 1.1 30132 23492 ? Sl 17:11 0:00 caddy -quiet -conf /tmp/serve-361831195/Caddyfile root 38 0.4 0.1 12680 3240 ? S 17:11 0:00 sh -c ps aux 2>&1 root 39 0.4 0.2 42440 5928 ? R 17:11 0:00 ps aux
旧サンドボックス環境を知っていると「psコマンドがマトモに動く!」という当たり前のことに感動してしまいますね。
PID 16番のCaddyはGo言語で書かれたWebサーバ実装で、php-fpmの前段で動いているようです。
lsof -p 16
lsofコマンドでCaddyがオープンしているファイルを確認してみました。
COMMAND PID USER FD TYPE DEVICE SIZE NODE NAME caddy 16 root cwd unknown /proc/16/cwd (readlink: No such file or directory) caddy 16 root rtd unknown /proc/16/root (readlink: No such file or directory) caddy 16 root txt REG 0,14 20099720 200 /usr/local/sbin/caddy caddy 16 root 0u CHR 0,0 5 /dev/null caddy 16 root 1u FIFO 0,12 2 host caddy 16 root 2u FIFO 0,12 3 host caddy 16 root 3u sock 0,5 5 can't identify protocol caddy 16 root 4u 0000 0,2 0 14 anon_inode caddy 16 root 5u sock 0,5 24 can't identify protocol caddy 16 root 6u sock 0,6 23 can't identify protocol
ファイルディスクリプタ3番5番6番がTCPだと思うんですが、「can't identify protocol」となっています。/proc
以下の未実装部分の影響でしょう。
ちなみにlsofコマンドは標準イメージ内に無かったのでUbuntuのバイナリをデプロイしましたが、普通に動きました。
ifconfig
eth0 Link encap:AMPR NET/ROM HWaddr inet addr:192.168.1.1 Mask:255.255.255.255 UP RUNNING MTU:0 Metric:1 RX packets:0 errors:0 dropped:0 overruns:0 frame:0 TX packets:0 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0 RX bytes:0 (0.0 B) TX bytes:0 (0.0 B) eth2 Link encap:AMPR NET/ROM HWaddr inet addr:169.254.8.1 Mask:255.255.255.255 inet6 addr: fe80::c001/128 Scope:Global UP RUNNING MTU:0 Metric:1 RX packets:0 errors:0 dropped:0 overruns:0 frame:0 TX packets:0 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0 RX bytes:0 (0.0 B) TX bytes:0 (0.0 B) lo Link encap:AMPR NET/ROM HWaddr inet addr:127.0.0.1 Mask:255.255.255.255 inet6 addr: ::1/128 Scope:Global UP RUNNING MTU:0 Metric:1 RX packets:0 errors:0 dropped:0 overruns:0 frame:0 TX packets:0 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0 RX bytes:0 (0.0 B) TX bytes:0 (0.0 B)
ifconfigコマンドもUbuntuから持ってきたものです。送受信パケット数がゼロなのは、現時点では未実装ということだと思います。
一部コマンドは動かない
体感値としては9割以上のコマンドがそれっぽい結果を返してくれるのですが、コマンドによっては異常終了するものもあります。
たとえばdfコマンドは未実装システムコールを呼んでいるのか「Function not implemented」というエラーが出て終了してしまいます。また、netstatを試すとサービス全体が刺さってしまい、インスタンスを再起動する羽目になりました。gVisor自体がまだ不安定なのかもしれません。
まとめ
そんなわけでGAE/SE PHP 7.2環境で色々試してみて、PHP 5.5環境よりは制約が断然少ない環境のように感じました。
これだけ普通のLinuxっぽければ言語本体の移植が速くても不思議は無いしアプリケーションの動作もほぼ問題なしだよね、という気持ちになります*1。逆に、以前のサンドボックスがマゾすぎたとも言えそうですね…。
gVisorの開発は続いていくはずですので、その意味でも今後ますます期待できる環境だと言えそうです。