nginxをmrubyで制御するモジュールngx_mruby 0.0.1をリリースしました

といっても、nginx固有のメソッドはクライアントに任意の文字列を返す事しかできませんが、とりあえず動くものを実装する事ができました。ということで、mod_mrubyの時と同様ngx_mruby 0.0.1としてGithubでリリースしたいと思います。もちろんmrubyに最初から含まれているメソッドは動きます。

ngx_mrubyとは

ここで一旦ngx_mrubyの簡単なおさらいをしておきます。ngx_mrubyはその名の通り、Apacheをmrubyで制御するためのモジュールmod_mrubyに対して、nginxをmrubyで制御するためのモジュールです。このモジュールによって、nginxを再起動することなく、Rubyスクリプトによってnginxの内部の様々な制御が簡単に行う(予定)事が可能になります。

また、mod_mrubyとApache(Nginx)の関係を図示してみたでも述べた通り、Apacheにmod_mruby、nginxにngx_mrubyを組み込む事で、mrubyでそれぞれApacheやnginx特有のAPIを吸収し、(ほぼ)同じmrubyのメソッドでApacheやnginxの違いを意識することなく制御できるようにしよう、というのが大きな目的の一つとしてあります。

例えば、mrubyスクリプトでクライアントに文字列を返したい場合は、

rputs("hello mruby world")

と記述することができます。これによって、Apacheだろうとnginxだろうと同じ動きをしますので、内部特有の実装を意識する必要がないため、様々なWebサーバソフトウェアが混在したシステムの拡張がrubyの記述で統一して行うことができ非常に簡単になります。詳しくは、なぜApacheにmrubyを組み込もうと思ったかを読んでいただくと、Webサーバの拡張支援に関する僕の意図がわかるとおもいます。

ngx_mrubyでHello Worldしてみよう

では早速ngx_mrubyを組み込んでみましょう。まだ、メソッドとしてはクライアントに文字列を返すメソッドrputsしか実装していないので、それを使って例の如くアクセスのあったクライアントに対して、Hello Worldを表示してみたいと思います。

まずはGithubからソースをダウンロードします。

git clone git://github.com/matsumoto-r/ngx_mruby.git

そして、configファイルを開いて、mrubyがインストールされているPathを変更して下さい。僕の場合は以下のようにしています。

mruby_root=/usr/local/src/mruby

nginx1.2.2stableをダウンロードします。

wget http://nginx.org/download/nginx-1.2.2.tar.gz

ダウンロード後、展開して以下のコマンドでngx_mrubyをモジュールとして指定してnginxそのものをコンパイルします。

./configure --add-module=/usr/local/src/ngx_mruby --prefix=/usr/local/nginx122
make
sudo make install

コンパイル後、nginx.confの設定に以下のような設定を加えます。

location /mruby {
    mrubyHandler /usr/local/nginx122/html/hello.mrb;
}

指定したmrubyスクリプト(/usr/local/nginx122/html/hello.mrb)に以下のメソッドを記述します。

Nginx.rputs(Time.now.to_s + " hello mruby world for nginx.")

では、nginxを起動します。

/usr/local/nginx122/sbin/nginx

そして、http://example.com/mrubyにアクセスしてみましょう。(example.comを自ドメインに置き換えて下さい)

Sat Jul 28 11:44:32 2012 hello mruby world for nginx.

と表示されたら成功です。ようこそ!mruby world for nginxへ!!

nginxを起動中でも、文字列を変えるとすぐに反映されることも確認して見て下さい。nginxはこのようにモジュールを組み込むために、nginxそのものをコンパイルする必要があります。そのため、ngx_mrubyを組み込むことで、再コンパイルや再起動をすることなくnginxの内部をコントロールできるのは、nginxにとって非常に有用なのではないかと考えています。nginxでもApacheでのmod_soみたいなのはあるのでしょうか。そのあたりは調べていません、

ngx_mrubyの今後

ベースの設計が大体できたので、今後はmod_mrubyにあわせて、以下のような実装を追加していこうと思っています。

  • メソッドを充実させる(mod_mrubyのメソッドに合わせる)
  • 処理のフック箇所を増やす
  • 設定の記述の仕方を検討
  • mrb_stateをスレッドでどのように使いまわすか検討
  • パフォーマンスを劣化させない実装を検討

これらはmod_mrubyの時でも散々言っていたことですね。とにかく、まだHello World程度ですが、動いてよかったです。0のものを1にするのは非常に大変ですが、0が1になった後は、どんどん効率良く実装する事ができるはずなので、これから勢い良く実装していこうと思っています。

いやー、とりあえず動くものができたので良かったです。