« 2007年04月 | メイン | 2007年07月 »

2007年06月19日

名前解決のコスト

アプリケーションのConfigとかでホスト名を使っていることが多いのだけど、ホスト名からIPへの名前解決、gethostbynameのコストが気になったのでテスト

テストのパターンは

  1. 名前解決なし
  2. /etc/hostsファイルに書いた場合
  3. DNSに問い合わせるパターン

をやってみた。

Perlのコードは以下。

#!/usr/bin/perl
use strict;
use warnings;
use Benchmark;
timethese(
    50000,
    {
        'no_lookup'    => sub { gethostbyname('10.101.100.51') },
        'hosts_lookup' => sub { gethostbyname('nomadscafe') },
        'named_lookup' => sub { gethostbyname('nomadscafe.jp') }
    }
);

環境はFedoraCore6のkernel-2.6.20です

実行結果

Benchmark: timing 50000 iterations of hosts_lookup, named_lookup, no_lookup...
hosts_lookup:  2 wallclock secs ( 0.71 usr +  0.83 sys =  1.54 CPU) @ 32467.53/s (n=50000)
named_lookup: 18 wallclock secs ( 1.47 usr +  1.99 sys =  3.46 CPU) @ 14450.87/s (n=50000)
 no_lookup:  0 wallclock secs ( 0.04 usr +  0.00 sys =  0.04 CPU) @ 1250000.00/s (n=50000)
            (warning: too few iterations for a reliable count)


hostsに書いたとしても、名前解決をするコストはかなり大きい。

ただ、設定ファイルの中身をIPにするのは、運用上のコストが高くなるので、
サーバへの配布時に自動変換とか考えることにしよう。


2007年06月15日

高速Webサーバ Nginxの組み込みPerlを使ってみる

NginxというWebサーバがあります。

ロシアの方がつくったもので、rambler.ruでも使われてます。
日本語情報がほぼ皆無ですが、このあたりで紹介されています。
機能的には、epoll,kqueueやsendfileなどがサポートされ、

  • rewrite, header書き換え
  • deflate
  • FastCGI
  • SSL
  • シンプルな負荷分散付きreverse proxy

等すでにLighttpdと比較しても遜色ない十分な機能が実装されてます。
パフォーマンス的にもLighttpdと同等かそれ以上でます。

珍しい機能として、「perlインタプリタの組み込み」があるので早速試してみます。Fedora Core6ではnginxはyumでインストールできます。perl_moduleも有効になってます
perl関連のドキュメントはここ

nginx.confはこんな感じ。
全体的には個人的はlighttdよりわかりやすいと思う。

events {
    use epoll;
}
http {
    sendfile       on;
    perl_modules /home/kazeburo/develop/lib;
    perl_require NginxTest/Calc.pm;
    server {
        listen       8080;
        location / {
            root   /home/kazeburo/html;
            index  index.html;
        }
        location /calctgt {
            perl NginxTest::Calc::handler;
        }
    }
}

perl_modulesでライブラリのパス、perl_requireで読み込むモジュール
「perl_require NginxTest/Calc.pm」がかなりイマイチ。

NginxTestは

package NginxTest::Calc;

use strict;
use warnings;
use nginx;

sub handler {
    my $r = shift;
    my $uri = URI->new( $r->uri, 'http' );
    $uri->query($r->args);
    $uri->query_param('cm', 0) unless $uri->query_param('cm');
    my $hyde;
    eval {
        $hyde = to_hyde( $uri->query_param('cm') );
    };
    $r->send_http_header('Content-Type', 'text/html; charset=utf-8');
    $r->print( "to_hyde(" . JSON::objToJson( { cm => $uri->query_param('cm'), hyde => $hyde } ) . ");" );
    return OK;
}

use行ははしょった。
$rがngixのオブジェクトでmod_perlのそれに似てる。

んで、nginxの起動

$ /usr/sbin/nginx -c nginx.conf


curlでテスト

$ curl "http://localhost:8080/calctgt=156"
to_hyde({"hyde":1.00,"cm":156});


ktkr!

ついでにApacheBenchでテスト。結構性能いいかも

$ ab -n 1000 -c 10  "http://localhost:8080/calctgt?cm=156"
Requests per second:    1457.78 [#/sec] (mean)
Time per request:       6.860 [ms] (mean)
Time per request:       0.686 [ms] (mean, across all concurrent requests)


デモはあとで用意する。かな