lighttpd で FastCGI / CGI-Application-FastCGI-0.01

Catalyst の雛形アプリ (catalyst.pl MyApp 叩くと出る Hello World! 的なやつ) をいろんなとこで動かしてベンチとってみた。

typester さんによる Catalyst を使ったベンチマークCatalyst そのもののベンチマークよりも lighttpd の速さに注目。ずいぶんと速いです。

はてなでも画像サーバーなどの static なコンテンツを返すサーバーに lighttpd を使えないもんかと、ベンチを取ったりしてます。ベンチ結果では、画像ファイルとかだと Apache2 とそこまで差は出ない感じなんですが、単に画像の転送時間が支配的になってるだけかもしれないし、ちょっとトラフィックの多いところに挟んで試してみようかなと思っています。

んで、この typester さんのベンチ結果の中で興味深いのは mod_perl + Apache 1.3 より lighttpd + mod_fastcgi の方が速いという結果です。これは結構意外でした。

ということで lighttpdFastCGI を使うってのは一体どんなもんなのかと、調べごとがてら試してみました。

FastCGI はずいぶん昔に商用のウェブサーバーでちょっと使ったことがあるのですが、インストールとか設定とかいろいろ面倒だなあという印象でした。が、lighttpd だと組み込みでインストールされてるのもあってえらい楽なんですね。引用元でも紹介されている Catalyst 開発者の一人の chansen 氏のサンプル を見れば簡単なのがわかると思います。

試しに CatalystFastCGI で動かすのでもいいかなと思ったのですが、それだとまんまでつまらないので CGI::Application を FastCGI で動かすモジュールを作って、それを動かしてみました。

CGI::App のかわりにこっちを継承すると、FastCGI 対応になります。さっき CPAN にあげておきました。(実は何気にモジュールの実装ではまった箇所がひとつ。CGI インスタンスを作る前に CGI::_reset_globals() を呼んでやらないとクエリが更新されない罠に陥いった。Catalyst::Engine::FastCGI 周りを見て解決策が分かったけどえらいバッドな香り。)

lighttpd は .configure; make; make install で ok、mod_fastcgi はデフォルトではいってます。lighttpd.conf で関係ありそうなとこは

server.modules = (
  "mod_access",
  "mod_fastcgi",
  "mod_accesslog" )  
)

fastcgi.server = (".fcgi" =>
 ( "myapp" =>
   ( 
    "socket" => "/tmp/myapp.socket",
    "bin-path" => "/home/naoya/public_html/fastcgi/hello.fcgi",
    "min-procs" => 5,
    "max-procs" => 10,
    "idle-timeout" => 20
    )
 )
)

ぐらいかな。bin-path は何のために指定してるのとかまだよくわかってない。

動かしたコードは、

#!/usr/local/bin/perl
use strict;
use lib qw (/home/naoya/perlhacks/CGI-Application-FastCGI/lib);
use MyApp::Hello;

my $webapp = MyApp::Hello->new;
$webapp->run;

__END__

という hello.fcgi ファイルと

package MyApp::Hello;
use strict;
use base qw (CGI::Application::FastCGI);

sub setup {
    my $app = shift;
    $app->start_mode('hello');
    $app->mode_param('__mode');
    $app->run_modes(
        'hello' => 'hello_func',
        'goodbye' => 'goodbye_func',
    );
}

sub hello_func {
    my $app = shift;
    return "Hello, World!!";
}

sub goodbye_func {
    my $app = shift;
    return "Good Bye ..";
}

1;

というしょぼい CGI::Application::FastCGI なモジュール。で、きちんと動きました。CGI 実装のときとのベンチの差を取ろうと思ったけど時間切れ。誰かよろしくとか言ってみるテスト。