mod_perl2環境でAmon2を動かす

Perl製WAFの場合、O/Rマッパーやレンダリングエンジンは好みのものを選択できたり、変更できたりすることが普通っぽいのであまり気にならないんだけど、その辺りにメリットを感じてたりするので個人的には比較的薄いWAFが好みです。そんなわけでAmon2

Amon2はPSGI/PlackベースのWAFなのでドキュメントでは

plackup BBS.psgi
HTTP::Server::PSGI: Accepting connections at http://0:5000/

という感じでスタンドアローンなPSGIサーバですぐに実行できるよと記述があって、実際簡単に実行できて開発の際はとても便利なんですが、Amon2ベースで作ろうとしているWebアプリを動かしたい環境はApache2+mod_perl2環境なので、さてどうすればmod_perl2環境でAmon2を動かすのか?というのが今回の問題。

PSGIとは?

PSGIはWeb+DB PRESS vol.55のPerl Hackers Hubで宮川達彦さんが書かれた記事が詳しいですが、PlackをベースにしたWebサーバレイヤを抽象化するための仕様です。PythonのWSGI / Rubyのrackに相当するもので、要はWAF側でPSGIに対応していればPSGIへのアダプタを用意するだけでWebサーバの差異をPSGIが吸収してくれます。

Web+DB PRESS vol.55のPerl Hackers Hubの記事は技術評論社のサイトでも公開されています。

よって、PSGI対応WAFであるAmon2をmod_perl環境で動かすということは、どうすればPSGI対応WAFをmod_perl環境で動かすことができるかってことになります。

なお、前に挙げたページにはスタンドアローンPSGIサーバやFastCGIでの起動方法にはサンプルコード付きで触れられていますが、

CGIやmod_perlについてはスタンドアロンで起動するのではなく,Webサーバから呼び出される形になるためplackupは利用できませんが,.psgiのパスをWebサーバから設定したり,.cgiファイルから呼び出す,といった形で簡単に再利用できます。

としか触れられていません。が、Webサーバから設定したりとあるのでhttpd.confで設定することが分かります。

実際に設定する

Amon2では

% amon2-setup.pl 作成するパッケージ名

を実行することで、作成するパッケージ名と同名のディレクトリ/そのディレクトリ以下に雛形が生成されます。具体的にはこんな感じになります。

% amon2-setup.pl sample
writing lib/sample.pm
writing lib/sample/Web.pm
writing tmpl/index.tt
writing app.psgi
writing Makefile.PL
writing t/00_compile.t
writing t/Util.pm
writing t/01_root.t
writing t/02_mech.t
writing xt/03_pod.t
mkpath: htdocs/static/img/
mkpath: htdocs/static/js/
writing lib/sample.pm
writing lib/sample/Web.pm
writing lib/sample/Web/Dispatcher.pm
writing config/development.pl
writing config/deployment.pl
writing config/test.pl
writing sql/my.sql
writing sql/sqlite3.sql
writing tmpl/index.tt
writing tmpl/include/layout.tt
writing htdocs/static/js/jquery-1.5.1.min.js
writing htdocs/static/css/blueprint/screen.css
writing htdocs/static/css/blueprint/print.css
writing htdocs/static/css/blueprint/ie.css
writing htdocs/static/css/main.css
writing t/00_compile.t
writing xt/02_perlcritic.t
writing .gitignore

% ll sample
total 16
-rw-r--r--  1 someone  staff  448  5 26 21:42 Makefile.PL
-rw-r--r--  1 someone  staff  454  5 26 21:42 app.psgi
drwxr-xr-x  2 someone  staff  170  5 26 21:42 config/
drwxr-xr-x  3 someone  staff  102  5 26 21:42 htdocs/
drwxr-xr-x  3 someone  staff  136  5 26 21:42 lib/
drwxr-xr-x  2 someone  staff  136  5 26 21:42 sql/
drwxr-xr-x  2 someone  staff  204  5 26 21:42 t/
drwxr-xr-x  3 someone  staff  136  5 26 21:42 tmpl/
drwxr-xr-x  2 someone  staff  136  5 26 21:42 xt/

で、このsampleディレクトリ直下に作成されるapp.psgiをhttpd.conf経由で、mod_perl呼び出し時に実行させてやるようにすれば良いわけですが、具体的にはどうすれば良いかってのは現状googleで検索してもなかなか見つかりません。

ですが、PSGIがWebサーバとWAF間の差異を吸収してくれるっていうことは、他のPSGI対応WAFでの起動方法が参考にできる、というかそのまま利用できるということでもあります。PSGIすごい!!

このページで扱われているWAFはMojoliciousですが、このWAFもPSGI対応なので、ここで紹介されている方法を参考に、今回はMacOS X10.6+Apache2.2.19+mod_perlの環境に、8001番ポートでVirtual Hostを立てて、そこでAmon2を実行させることにします(なので以下のサンプルのパスは環境に合わせて読み替えてください)。

% less httpd-vircualhost.conf
Listen 8001

<VirtualHost *:8001>
    ServerAdmin admin@example.jp
    DocumentRoot "/Users/someone/sample/htdocs/static"
    ErrorLog "logs/error_log"
    CustomLog "logs/access_log" common

    <Directory "/Users/someone/sample/htdocs/static">
        AllowOverride all
        Options Indexes FollowSymLinks execCGI -MultiViews
        Order allow,deny
        Allow from all
    </Directory>
    <Location />
        SetHandler perl-script
        PerlHandler Plack::Handler::Apache2

        PerlSetVar psgi_app /Users/someone/sample/app.psgi
    </Location>
</VirtualHost>

こんな感じのconfファイルをhttpd.confにインクルードしてapacheを再起動するとそのサーバの8001番ポートでAmon2が実行できるようになります。