Walrus,Digit. | 一覧 | 検索 | 更新履歴(RSS) | 新規作成
はてなブックマークに追加 はてなブックマークを表示 編集 | 編集(管理者用) | 差分

Perlモジュール/Net::FelicaFromNet

編集

FelicaToNetからのデータを受信するためのベースクラスです。

まだ、PODドキュメントもほとんど書かれていませんし、配布ファイルにもまとめられておらず、ソースがあるだけです。 分かる人だけが使ってください。

使い方

編集

Perlのライブラリ検索パス内に、適切に配置してください。

配置が正しくできていれば、以下のコマンドラインで、受信を開始することができます。 起動後に、FelicaToNetで接続、読み取り、切断などをやってみてください。

perl -MNet::FelicaFromNet -e "Net::FelicaFromNet->new->start;"

ライブラリとしては、オブジェクトを生成し、startを呼ぶことで上記と同様の受信開始ができます。 startを呼ぶ前に、callbackメソッドにサブルーチンのリファレンスを渡しておくと、FelicaToNetからのデータ受信時に、そのコールバックルーチンが呼ばれます。 コールバックサブルーチンに渡される引数は、Net::FelicaFromNet?オブジェクト、IO::Socketオブジェクト、以下のキーを持つハッシュデータです。

キー内容
event発生したイベントを表わす、"NEW CLIENT"、"NEW MESSAGE"、"END CLIENT"のいずれかの文字列
addressデータの受信下を現すIPアドレス(文字列)
clientFelicaToNetで設定したクライアントID
felicaFelicaToNetで読み取ったカードID(カードを外した時は"0")
time読み取りを行った時刻

コールバックサブルーチンの内容は、ソース内にある、デフォルトで使用されるdefault_callbackサブルーチンを参考にしてください。

ソース

package Net::FelicaFromNet;

use strict;
use base qw(Class::Accessor);
use vars qw($VERSION);
use IO::Socket;
use IO::Select;

$VERSION = '0.01';

Net::FelicaFromNet->mk_accessors(qw(port listener selecter callback));

sub new {
  my $class = shift;
  my $port  = (@_) ? shift : 4321;
  my $self  = bless {}, $class;
  $self->port($port);
  return $self;
}

sub start {
  my $self = shift;
  my $port = $self->port;
  # lsitenerの取得
  my $listener = $self->listener;
  if (not $self->listener and $port) {
    $listener = IO::Socket::INET->new(
      LocalPort => $port,
      Listen    => SOMAXCONN,
      Proto     => 'tcp',
      Reuse     => 1,
    );
    die "listen できませんでした。 $!\n" unless ( $listener );
    $self->listener($listener);
  }
  # listen
  my $callback = $self->callback || \&default_callback;
  my $selecter = IO::Select->new;
  $selecter->add($listener);
  $self->selecter($selecter);
  while ($self->selecter) {
    my ($active_socks) = IO::Select->select($self->selecter,undef,undef,undef);
    foreach my $sock (@{$active_socks}){
      if ($sock == $self->listener){
        my $new_sock = $sock->accept;
        my $new_addr = $new_sock->peerhost;
        &{$callback}($self, $new_sock, {'event' => "NEW CLIENT", 'address' => $new_addr});
        $selecter->add($new_sock) if ($new_sock);
      } else {
        my $addr = $sock->peerhost;
        my $buf = <$sock>;
        if ( $buf ){
          chomp($buf);
          my ($client, $felica, $time) = split(/,/, $buf);
          &{$callback}($self, $sock, {'event' => "NEW MESSAGE", 'address' => $addr, 'client' => $client, 'felica' => $felica, 'time' => $time});
          $sock->flush() if ($sock);
        } else {
          &{$callback}($self, $sock, {'event' => "END CLIENT", 'address' => $addr});
          $selecter->remove($sock);
          $sock->close() if ($sock);
        }
      }
    }
  }
  return $self->listener;
}

sub default_callback {
  my $self  = shift;
  my $sock  = shift;
  my $event = shift;
  if ($event->{'event'} =~ /^(NEW|END) CLIENT$/) {
    printf("[%s] %s\n", $event->{'event'}, $event->{'address'});
  } elsif ($event->{'event'} eq 'NEW MESSAGE') {
    printf("[%s] %s:%s %s at %s\n", (map { $event->{$_} } qw(event address client felica time)));
  } else {
    eval '
      use Data::Dumper;
      local $Data::Dumper::Indent = 0;
      local $Data::Dumper::Sortkeys = 1;
    ';
    printf("[%s]\n%s\n", 'UNKOWN', Dumper($event));
  }
}

1;

__END__
=head1 NAME

Net::FelicaFromNet - Receiver base module for FelicaToNet

=head1 SYNOPSIS

 perl -MNet::FelicaFromNet -e "Net::FelicaFromNet->new->start;"

=head1 SEE ALSO

L<http://www.mobiquitous.com/pub/sd200501-2.html#5>

=head1 COPYRIGHT

Copyright 2006-2006 Makio Tsukamoto <tsukamoto@gmail.com>

This library is free software; you can redistribute it
and/or modify it under the same terms as Perl itself.

=cut

コメント

コメントスパムがひどいためこのページのコメント欄を削除しました。コメントしたい方は暫定的に「掲示板」のページへお願いいたします。