camel

POE����ή�Ԥ��Ƥ��ޤ����伫��POE�Ϥ��礯���礯�ȤäƤ���ΤǤ����������С��ϤȤˤ������饤����ȤȤʤ�Ȥ���ۤɻȤäƤ��ޤ���

��ͳ�ϡ��ʲ��Ǥ�����ޤ���

��ͳ�ϡ���ä�ñ�㡣���Ψ������Ǥ���

�ʲ������������������Ǥ�10000bytes�Υ���ƥ�Ȥ�Ʊ�������С���100����˹ԤäƤ��ޤ���

% perl lwp-bench.pl 0
Elapsed: 2.245773 seconds                                                       
Connection: close       100
% perl lwp-bench.pl 1
Elapsed: 0.928301 seconds                                                       
Connection: (N/A)       99
Connection: Keep-Alive  1
% perl poe-bench.pl 1
Elapsed: 19.593628 seconds
% perl poe-bench.pl 10
Elapsed: 5.451616 seconds

POE���������٤������狼��ˤʤ뤫�Ȼפ��ޤ���ñ���٤������ǤϤʤ������꡼���äȿ����ޤ��������ƥ����ɤϤ����ʣ���Ǥ���

�����ͤ��Ƥߤ�������ǡ�POE����Ʊ���ǥ��٥�Ȥ��������Ȥ������������Ȥ����Ӥ��ޤ��������ƥ��٥�Ȥξ夲�����Ȥ����Τϡ�OS�ˤ����Ƥ���ڤ��������ǤϤʤ��ΤǤ������Ƥ�桼�������֤ǡ�������preemptive�ǤϤʤ�cooprative�ˤ��ʤ���Фʤ�ʤ�POE���ڤ��ʤ��Τ������Τ��ȤʤΤǤ���

�����顢���POE�����Ѥ���Ʊ���������򤱤��ʤ���Τ˸��ꤷ�Ƥ��ޤ���Xango�Τ褦���礭��Υե졼�����ˤϸ����Ƥ��ޤ�����Ʊ��ۥ��Ȥ���ʣ���Υ���ƥ�Ĥ��äƤ���Ȥ������ˤϡ���������Ʊ���ˤ���ޤǤ�ʤ����Ȥ�����¿���������Ƥ����������¦�Υ����С����Ф�����٤��㤤�ΤǤ���

���������¦�Υ����С���٤ϡ�keep_alive��Ȥ����Ȥǹ��˲�����ޤ���LWP::UserAgent�ϼ¤�keep_alive��������Ƶפ�����LWP::ConnCache�Υɥ�����ȤǤ�"experimental"�ȤʤäƤ��Ƥ⡢���Ǥϰ��ꤷ�ƻȤ��Ƥ��ޤ�����������Ѥ��ʤ���Ϥʤ��ΤǤ���

POE��Web���饤����ȤǻȤ����ɤ����ϡ����ץꥱ�������ʣ�������Ȥ˥����������뤫���礭���Ǥ��礦�����ξ��ϡ�POE�Ϥ��꤬�������ä� proxy server ��񤯾��Ͻ������ޤ������ξ�硢���ץꥱ�������ϥ����С��Ǥ⤢�ꥯ�饤����ȤǤ⤢��Τ�POE��Ȥ��Τ˽�ʬ�ʥ��󥻥�ƥ��֤Ȥʤ�ޤ���

�����Ǥʤ����ϡ�my $ua = LWP::UserAgent->new(keep_alive => 1)�Ȥ��ơ�����$ua�򽪻ϻȤ��󤹤Τ��������С��Τ���ˤ⡢���饤����ȤΤ���ˤ⡢�����Ƥʤˤ���ץ�����ޡ��Τ���ˤ�褤���Ȼפ��ޤ���

;�̤ˤʤ�ޤ����������benchmark�Ǥϡ�chargen�Ȥ����ȥ�ӥ���ʥ����С�¦�ץ�������Ȥ��ޤ�����

�������򸫤�Ф��狼��ˤʤ�Ȥ��ꡢhttp://wherever/path/to/chargen/NUMBER�ǡ�NUMBER bytes��ʸ�����ư��������Ȥ�����ΤǤ���mod_perl��ư��������Ū�ʥ��ߡ�����ƥ�Ȥ�Ȥ���ꤺ�äȹ�®�Ǥ�(Gbit Ether�򿿤ù��ˤǤ��ޤ�)���٥���ޡ����ˤ����Ѥ�����������������ʬ�Υ����С��ǡ�

���饤����ȤΥ������ϡ��ʲ��ΤȤ���Ǥ���

Enjoy!

Dan the Man with Too Many Ways to Access HTTP

lwp-bench.pl
#!/usr/local/bin/perl
use strict;
use warnings;
use Time::HiRes qw/time/;
use LWP::UserAgent;

my $base       = 'http://your.server/path/to/chargen';
my $keep_alive = shift || 0;
my $size       = shift || 100000;
my $ntimes     = shift || 100;
my $ua         = LWP::UserAgent->new( keep_alive => $keep_alive );
my %conn_stat;

local ( $|, $\, $, ) = ( 1, "\r", "\t" );
my $total_bytes = 0;

my $started = time();
for my $n (1.. $ntimes){
    my $uri = "$base/$size/$n";
    my $res = $ua->get($uri);
    die $res->code unless $res->is_success;
    no warnings 'uninitialized';
    my $conn = $res->headers->header('Connection');
    $conn_stat{$conn}++;
    $total_bytes += length $res->content;
    print " " x 80;
    print $res->request->uri, $res->code, $conn;
}

print " " x 80;
printf "Elapsed: %f seconds\n", time() - $started;

local ( $|, $\, $, ) = ( 1, "\n", "\t" );
for my $k ( sort { $conn_stat{$b} <=> $conn_stat{$a} } keys %conn_stat ) {
    my $conn = $k || '(N/A)';
    print "Connection: $conn", $conn_stat{$k};
}
print `ps uxww -p $$`
poe-bench.pl
#!/usr/local/bin/perl;
use strict;
use warnings;

use HTTP::Request;
use POE qw(Component::Client::HTTP);
use Time::HiRes qw/time/;
$| = 1;
my $base  = 'http://api.dan.co.jp/chargen';
my $mph   = shift || 4;
 my $size = shift || 10000;
my $count = shift || 100;
my $started;

my $pool = POE::Component::Client::Keepalive->new(
    keep_alive   => 120,  # seconds to keep connections alive
    max_open     => 100,  # max concurrent connections - total
    max_per_host => $mph, # max concurrent connections - per host
    timeout      => 15,   # max time (seconds) to establish a new connection
);

POE::Component::Client::HTTP->spawn(
    Alias             => 'ua',    # defaults to 'weeble'
    Timeout           => 20,      # defaults to 180 seconds
    ConnectionManager => $pool
);

POE::Session->create(
    inline_states => {
        _start => sub {
            $started = time();
            for my $i ( 1 .. $count ) {
                my $req = HTTP::Request->new( GET => "$base/$size/$i" );
                POE::Kernel->post( 'ua', 'request', 'response', $req );
            }
        },
        _stop => sub {
            print " " x 80;
            printf "Elapsed: %f seconds\n", time() - $started;
            $_[KERNEL]->stop;
        },
        response => sub {
            my $req = $_[ARG0]->[0];
            my $res = $_[ARG1]->[0];
            print " " x 80, "\r";
            print join( "\t", $res->request->uri, $res->code ), "\r";
          }
    },
);

POE::Kernel->run();
print `ps uxww -p $$`;
exit;